1 /*
   2  * Copyright (c) 2018, 2025, 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.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  */
  23 
  24 /*
  25  * @test
  26  * @key randomness
  27  *
  28  * @library /test/lib
  29  * @modules jdk.incubator.vector
  30  * @run testng/othervm/timeout=300 -ea -esa -Xbatch -XX:-TieredCompilation Double64VectorTests
  31  */
  32 
  33 // -- This file was mechanically generated: Do not edit! -- //
  34 
  35 import jdk.incubator.vector.VectorShape;
  36 import jdk.incubator.vector.VectorSpecies;
  37 import jdk.incubator.vector.VectorShuffle;
  38 import jdk.incubator.vector.VectorMask;
  39 import jdk.incubator.vector.VectorOperators;
  40 import jdk.incubator.vector.Vector;
  41 
  42 import jdk.incubator.vector.DoubleVector;
  43 
  44 import org.testng.Assert;
  45 import org.testng.annotations.DataProvider;
  46 import org.testng.annotations.Test;
  47 
  48 import java.lang.Integer;
  49 import java.util.List;
  50 import java.util.Arrays;
  51 import java.util.function.BiFunction;
  52 import java.util.function.IntFunction;
  53 import java.util.Objects;
  54 import java.util.stream.Collectors;
  55 import java.util.stream.Stream;
  56 
  57 @Test
  58 public class Double64VectorTests extends AbstractVectorTest {
  59 
  60     static final VectorSpecies<Double> SPECIES =
  61                 DoubleVector.SPECIES_64;
  62 
  63     static final int INVOC_COUNT = Integer.getInteger("jdk.incubator.vector.test.loop-iterations", 100);
  64 
  65     static DoubleVector bcast_vec = DoubleVector.broadcast(SPECIES, (double)10);
  66 
  67 
  68     // for floating point addition reduction ops that may introduce rounding errors
  69     private static final double RELATIVE_ROUNDING_ERROR_FACTOR_ADD = (double)10.0;
  70 
  71     // for floating point multiplication reduction ops that may introduce rounding errors
  72     private static final double RELATIVE_ROUNDING_ERROR_FACTOR_MUL = (double)50.0;
  73 
  74     static final int BUFFER_REPS = Integer.getInteger("jdk.incubator.vector.test.buffer-vectors", 25000 / 64);
  75 
  76     static void assertArraysStrictlyEquals(double[] r, double[] a) {
  77         for (int i = 0; i < a.length; i++) {
  78             long ir = Double.doubleToRawLongBits(r[i]);
  79             long ia = Double.doubleToRawLongBits(a[i]);
  80             if (ir != ia) {
  81                 Assert.fail(String.format("at index #%d, expected = %016X, actual = %016X", i, ia, ir));
  82             }
  83         }
  84     }
  85 
  86     interface FUnOp {
  87         double apply(double a);
  88     }
  89 
  90     static void assertArraysEquals(double[] r, double[] a, FUnOp f) {
  91         int i = 0;
  92         try {
  93             for (; i < a.length; i++) {
  94                 Assert.assertEquals(r[i], f.apply(a[i]));
  95             }
  96         } catch (AssertionError e) {
  97             Assert.assertEquals(r[i], f.apply(a[i]), "at index #" + i + ", input = " + a[i]);
  98         }
  99     }
 100 
 101     interface FUnArrayOp {
 102         double[] apply(double a);
 103     }
 104 
 105     static void assertArraysEquals(double[] r, double[] a, FUnArrayOp f) {
 106         int i = 0;
 107         try {
 108             for (; i < a.length; i += SPECIES.length()) {
 109                 Assert.assertEquals(Arrays.copyOfRange(r, i, i+SPECIES.length()),
 110                   f.apply(a[i]));
 111             }
 112         } catch (AssertionError e) {
 113             double[] ref = f.apply(a[i]);
 114             double[] res = Arrays.copyOfRange(r, i, i+SPECIES.length());
 115             Assert.assertEquals(res, ref, "(ref: " + Arrays.toString(ref)
 116               + ", res: " + Arrays.toString(res)
 117               + "), at index #" + i);
 118         }
 119     }
 120 
 121     static void assertArraysEquals(double[] r, double[] a, boolean[] mask, FUnOp f) {
 122         int i = 0;
 123         try {
 124             for (; i < a.length; i++) {
 125                 Assert.assertEquals(r[i], mask[i % SPECIES.length()] ? f.apply(a[i]) : a[i]);
 126             }
 127         } catch (AssertionError e) {
 128             Assert.assertEquals(r[i], mask[i % SPECIES.length()] ? f.apply(a[i]) : a[i], "at index #" + i + ", input = " + a[i] + ", mask = " + mask[i % SPECIES.length()]);
 129         }
 130     }
 131 
 132     interface FReductionOp {
 133         double apply(double[] a, int idx);
 134     }
 135 
 136     interface FReductionAllOp {
 137         double apply(double[] a);
 138     }
 139 
 140     static void assertReductionArraysEquals(double[] r, double rc, double[] a,
 141                                             FReductionOp f, FReductionAllOp fa) {
 142         assertReductionArraysEquals(r, rc, a, f, fa, (double)0.0);
 143     }
 144 
 145     static void assertReductionArraysEquals(double[] r, double rc, double[] a,
 146                                             FReductionOp f, FReductionAllOp fa,
 147                                             double relativeErrorFactor) {
 148         int i = 0;
 149         try {
 150             Assert.assertEquals(rc, fa.apply(a), Math.ulp(rc) * relativeErrorFactor);
 151             for (; i < a.length; i += SPECIES.length()) {
 152                 Assert.assertEquals(r[i], f.apply(a, i), Math.ulp(r[i]) * relativeErrorFactor);
 153             }
 154         } catch (AssertionError e) {
 155             Assert.assertEquals(rc, fa.apply(a), Math.ulp(rc) * relativeErrorFactor, "Final result is incorrect!");
 156             Assert.assertEquals(r[i], f.apply(a, i), Math.ulp(r[i]) * relativeErrorFactor, "at index #" + i);
 157         }
 158     }
 159 
 160     interface FReductionMaskedOp {
 161         double apply(double[] a, int idx, boolean[] mask);
 162     }
 163 
 164     interface FReductionAllMaskedOp {
 165         double apply(double[] a, boolean[] mask);
 166     }
 167 
 168     static void assertReductionArraysEqualsMasked(double[] r, double rc, double[] a, boolean[] mask,
 169                                             FReductionMaskedOp f, FReductionAllMaskedOp fa) {
 170         assertReductionArraysEqualsMasked(r, rc, a, mask, f, fa, (double)0.0);
 171     }
 172 
 173     static void assertReductionArraysEqualsMasked(double[] r, double rc, double[] a, boolean[] mask,
 174                                             FReductionMaskedOp f, FReductionAllMaskedOp fa,
 175                                             double relativeError) {
 176         int i = 0;
 177         try {
 178             Assert.assertEquals(rc, fa.apply(a, mask), Math.abs(rc * relativeError));
 179             for (; i < a.length; i += SPECIES.length()) {
 180                 Assert.assertEquals(r[i], f.apply(a, i, mask), Math.abs(r[i] *
 181 relativeError));
 182             }
 183         } catch (AssertionError e) {
 184             Assert.assertEquals(rc, fa.apply(a, mask), Math.abs(rc * relativeError), "Final result is incorrect!");
 185             Assert.assertEquals(r[i], f.apply(a, i, mask), Math.abs(r[i] * relativeError), "at index #" + i);
 186         }
 187     }
 188 
 189     interface FReductionOpLong {
 190         long apply(double[] a, int idx);
 191     }
 192 
 193     interface FReductionAllOpLong {
 194         long apply(double[] a);
 195     }
 196 
 197     static void assertReductionLongArraysEquals(long[] r, long rc, double[] a,
 198                                             FReductionOpLong f, FReductionAllOpLong fa) {
 199         int i = 0;
 200         try {
 201             Assert.assertEquals(rc, fa.apply(a));
 202             for (; i < a.length; i += SPECIES.length()) {
 203                 Assert.assertEquals(r[i], f.apply(a, i));
 204             }
 205         } catch (AssertionError e) {
 206             Assert.assertEquals(rc, fa.apply(a), "Final result is incorrect!");
 207             Assert.assertEquals(r[i], f.apply(a, i), "at index #" + i);
 208         }
 209     }
 210 
 211     interface FReductionMaskedOpLong {
 212         long apply(double[] a, int idx, boolean[] mask);
 213     }
 214 
 215     interface FReductionAllMaskedOpLong {
 216         long apply(double[] a, boolean[] mask);
 217     }
 218 
 219     static void assertReductionLongArraysEqualsMasked(long[] r, long rc, double[] a, boolean[] mask,
 220                                             FReductionMaskedOpLong f, FReductionAllMaskedOpLong fa) {
 221         int i = 0;
 222         try {
 223             Assert.assertEquals(rc, fa.apply(a, mask));
 224             for (; i < a.length; i += SPECIES.length()) {
 225                 Assert.assertEquals(r[i], f.apply(a, i, mask));
 226             }
 227         } catch (AssertionError e) {
 228             Assert.assertEquals(rc, fa.apply(a, mask), "Final result is incorrect!");
 229             Assert.assertEquals(r[i], f.apply(a, i, mask), "at index #" + i);
 230         }
 231     }
 232 
 233     interface FBoolReductionOp {
 234         boolean apply(boolean[] a, int idx);
 235     }
 236 
 237     static void assertReductionBoolArraysEquals(boolean[] r, boolean[] a, FBoolReductionOp f) {
 238         int i = 0;
 239         try {
 240             for (; i < a.length; i += SPECIES.length()) {
 241                 Assert.assertEquals(r[i], f.apply(a, i));
 242             }
 243         } catch (AssertionError e) {
 244             Assert.assertEquals(r[i], f.apply(a, i), "at index #" + i);
 245         }
 246     }
 247 
 248     interface FMaskReductionOp {
 249         int apply(boolean[] a, int idx);
 250     }
 251 
 252     static void assertMaskReductionArraysEquals(int[] r, boolean[] a, FMaskReductionOp f) {
 253         int i = 0;
 254         try {
 255             for (; i < a.length; i += SPECIES.length()) {
 256                 Assert.assertEquals(r[i], f.apply(a, i));
 257             }
 258         } catch (AssertionError e) {
 259             Assert.assertEquals(r[i], f.apply(a, i), "at index #" + i);
 260         }
 261     }
 262 
 263     static void assertRearrangeArraysEquals(double[] r, double[] a, int[] order, int vector_len) {
 264         int i = 0, j = 0;
 265         try {
 266             for (; i < a.length; i += vector_len) {
 267                 for (j = 0; j < vector_len; j++) {
 268                     Assert.assertEquals(r[i+j], a[i+order[i+j]]);
 269                 }
 270             }
 271         } catch (AssertionError e) {
 272             int idx = i + j;
 273             Assert.assertEquals(r[i+j], a[i+order[i+j]], "at index #" + idx + ", input = " + a[i+order[i+j]]);
 274         }
 275     }
 276 
 277     static void assertcompressArraysEquals(double[] r, double[] a, boolean[] m, int vector_len) {
 278         int i = 0, j = 0, k = 0;
 279         try {
 280             for (; i < a.length; i += vector_len) {
 281                 k = 0;
 282                 for (j = 0; j < vector_len; j++) {
 283                     if (m[(i + j) % SPECIES.length()]) {
 284                         Assert.assertEquals(r[i + k], a[i + j]);
 285                         k++;
 286                     }
 287                 }
 288                 for (; k < vector_len; k++) {
 289                     Assert.assertEquals(r[i + k], (double)0);
 290                 }
 291             }
 292         } catch (AssertionError e) {
 293             int idx = i + k;
 294             if (m[(i + j) % SPECIES.length()]) {
 295                 Assert.assertEquals(r[idx], a[i + j], "at index #" + idx);
 296             } else {
 297                 Assert.assertEquals(r[idx], (double)0, "at index #" + idx);
 298             }
 299         }
 300     }
 301 
 302     static void assertexpandArraysEquals(double[] r, double[] a, boolean[] m, int vector_len) {
 303         int i = 0, j = 0, k = 0;
 304         try {
 305             for (; i < a.length; i += vector_len) {
 306                 k = 0;
 307                 for (j = 0; j < vector_len; j++) {
 308                     if (m[(i + j) % SPECIES.length()]) {
 309                         Assert.assertEquals(r[i + j], a[i + k]);
 310                         k++;
 311                     } else {
 312                         Assert.assertEquals(r[i + j], (double)0);
 313                     }
 314                 }
 315             }
 316         } catch (AssertionError e) {
 317             int idx = i + j;
 318             if (m[idx % SPECIES.length()]) {
 319                 Assert.assertEquals(r[idx], a[i + k], "at index #" + idx);
 320             } else {
 321                 Assert.assertEquals(r[idx], (double)0, "at index #" + idx);
 322             }
 323         }
 324     }
 325 
 326     static void assertSelectFromTwoVectorEquals(double[] r, double[] order, double[] a, double[] b, int vector_len) {
 327         int i = 0, j = 0;
 328         boolean is_exceptional_idx = false;
 329         int idx = 0, wrapped_index = 0, oidx = 0;
 330         try {
 331             for (; i < a.length; i += vector_len) {
 332                 for (j = 0; j < vector_len; j++) {
 333                     idx = i + j;
 334                     wrapped_index = Math.floorMod((int)order[idx], 2 * vector_len);
 335                     is_exceptional_idx = wrapped_index >= vector_len;
 336                     oidx = is_exceptional_idx ? (wrapped_index - vector_len) : wrapped_index;
 337                     Assert.assertEquals(r[idx], (is_exceptional_idx ? b[i + oidx] : a[i + oidx]));
 338                 }
 339             }
 340         } catch (AssertionError e) {
 341             Assert.assertEquals(r[idx], (is_exceptional_idx ? b[i + oidx] : a[i + oidx]), "at index #" + idx + ", order = " + order[idx] + ", a = " + a[i + oidx] + ", b = " + b[i + oidx]);
 342         }
 343     }
 344 
 345     static void assertSelectFromArraysEquals(double[] r, double[] a, double[] order, int vector_len) {
 346         int i = 0, j = 0;
 347         try {
 348             for (; i < a.length; i += vector_len) {
 349                 for (j = 0; j < vector_len; j++) {
 350                     Assert.assertEquals(r[i+j], a[i+(int)order[i+j]]);
 351                 }
 352             }
 353         } catch (AssertionError e) {
 354             int idx = i + j;
 355             Assert.assertEquals(r[i+j], a[i+(int)order[i+j]], "at index #" + idx + ", input = " + a[i+(int)order[i+j]]);
 356         }
 357     }
 358 
 359     static void assertRearrangeArraysEquals(double[] r, double[] a, int[] order, boolean[] mask, int vector_len) {
 360         int i = 0, j = 0;
 361         try {
 362             for (; i < a.length; i += vector_len) {
 363                 for (j = 0; j < vector_len; j++) {
 364                     if (mask[j % SPECIES.length()])
 365                          Assert.assertEquals(r[i+j], a[i+order[i+j]]);
 366                     else
 367                          Assert.assertEquals(r[i+j], (double)0);
 368                 }
 369             }
 370         } catch (AssertionError e) {
 371             int idx = i + j;
 372             if (mask[j % SPECIES.length()])
 373                 Assert.assertEquals(r[i+j], a[i+order[i+j]], "at index #" + idx + ", input = " + a[i+order[i+j]] + ", mask = " + mask[j % SPECIES.length()]);
 374             else
 375                 Assert.assertEquals(r[i+j], (double)0, "at index #" + idx + ", input = " + a[i+order[i+j]] + ", mask = " + mask[j % SPECIES.length()]);
 376         }
 377     }
 378 
 379     static void assertSelectFromArraysEquals(double[] r, double[] a, double[] order, boolean[] mask, int vector_len) {
 380         int i = 0, j = 0;
 381         try {
 382             for (; i < a.length; i += vector_len) {
 383                 for (j = 0; j < vector_len; j++) {
 384                     if (mask[j % SPECIES.length()])
 385                          Assert.assertEquals(r[i+j], a[i+(int)order[i+j]]);
 386                     else
 387                          Assert.assertEquals(r[i+j], (double)0);
 388                 }
 389             }
 390         } catch (AssertionError e) {
 391             int idx = i + j;
 392             if (mask[j % SPECIES.length()])
 393                 Assert.assertEquals(r[i+j], a[i+(int)order[i+j]], "at index #" + idx + ", input = " + a[i+(int)order[i+j]] + ", mask = " + mask[j % SPECIES.length()]);
 394             else
 395                 Assert.assertEquals(r[i+j], (double)0, "at index #" + idx + ", input = " + a[i+(int)order[i+j]] + ", mask = " + mask[j % SPECIES.length()]);
 396         }
 397     }
 398 
 399     static void assertBroadcastArraysEquals(double[] r, double[] a) {
 400         int i = 0;
 401         for (; i < a.length; i += SPECIES.length()) {
 402             int idx = i;
 403             for (int j = idx; j < (idx + SPECIES.length()); j++)
 404                 a[j]=a[idx];
 405         }
 406 
 407         try {
 408             for (i = 0; i < a.length; i++) {
 409                 Assert.assertEquals(r[i], a[i]);
 410             }
 411         } catch (AssertionError e) {
 412             Assert.assertEquals(r[i], a[i], "at index #" + i + ", input = " + a[i]);
 413         }
 414     }
 415 
 416     interface FBinOp {
 417         double apply(double a, double b);
 418     }
 419 
 420     interface FBinMaskOp {
 421         double apply(double a, double b, boolean m);
 422 
 423         static FBinMaskOp lift(FBinOp f) {
 424             return (a, b, m) -> m ? f.apply(a, b) : a;
 425         }
 426     }
 427 
 428     static void assertArraysEqualsAssociative(double[] rl, double[] rr, double[] a, double[] b, double[] c, FBinOp f) {
 429         int i = 0;
 430         try {
 431             for (; i < a.length; i++) {
 432                 //Left associative
 433                 Assert.assertEquals(rl[i], f.apply(f.apply(a[i], b[i]), c[i]));
 434 
 435                 //Right associative
 436                 Assert.assertEquals(rr[i], f.apply(a[i], f.apply(b[i], c[i])));
 437 
 438                 //Results equal sanity check
 439                 Assert.assertEquals(rl[i], rr[i]);
 440             }
 441         } catch (AssertionError e) {
 442             Assert.assertEquals(rl[i], f.apply(f.apply(a[i], b[i]), c[i]), "left associative test at index #" + i + ", input1 = " + a[i] + ", input2 = " + b[i] + ", input3 = " + c[i]);
 443             Assert.assertEquals(rr[i], f.apply(a[i], f.apply(b[i], c[i])), "right associative test at index #" + i + ", input1 = " + a[i] + ", input2 = " + b[i] + ", input3 = " + c[i]);
 444             Assert.assertEquals(rl[i], rr[i], "Result checks not equal at index #" + i + "leftRes = " + rl[i] + ", rightRes = " + rr[i]);
 445         }
 446     }
 447 
 448    static void assertArraysEqualsAssociative(double[] rl, double[] rr, double[] a, double[] b, double[] c, boolean[] mask, FBinOp f) {
 449        assertArraysEqualsAssociative(rl, rr, a, b, c, mask, FBinMaskOp.lift(f));
 450    }
 451 
 452     static void assertArraysEqualsAssociative(double[] rl, double[] rr, double[] a, double[] b, double[] c, boolean[] mask, FBinMaskOp f) {
 453         int i = 0;
 454         boolean mask_bit = false;
 455         try {
 456             for (; i < a.length; i++) {
 457                 mask_bit = mask[i % SPECIES.length()];
 458                 //Left associative
 459                 Assert.assertEquals(rl[i], f.apply(f.apply(a[i], b[i], mask_bit), c[i], mask_bit));
 460 
 461                 //Right associative
 462                 Assert.assertEquals(rr[i], f.apply(a[i], f.apply(b[i], c[i], mask_bit), mask_bit));
 463 
 464                 //Results equal sanity check
 465                 Assert.assertEquals(rl[i], rr[i]);
 466             }
 467         } catch (AssertionError e) {
 468             Assert.assertEquals(rl[i], f.apply(f.apply(a[i], b[i], mask_bit), c[i], mask_bit), "left associative masked test at index #" + i + ", input1 = " + a[i] + ", input2 = " + b[i] + ", input3 = " + c[i] + ", mask = " + mask_bit);
 469             Assert.assertEquals(rr[i], f.apply(a[i], f.apply(b[i], c[i], mask_bit), mask_bit), "right associative masked test at index #" + i + ", input1 = " + a[i] + ", input2 = " + b[i] + ", input3 = " + c[i] + ", mask = " + mask_bit);
 470             Assert.assertEquals(rl[i], rr[i], "Result checks not equal at index #" + i + "leftRes = " + rl[i] + ", rightRes = " + rr[i]);
 471         }
 472     }
 473 
 474     static void assertArraysEquals(double[] r, double[] a, double[] b, FBinOp f) {
 475         int i = 0;
 476         try {
 477             for (; i < a.length; i++) {
 478                 Assert.assertEquals(r[i], f.apply(a[i], b[i]));
 479             }
 480         } catch (AssertionError e) {
 481             Assert.assertEquals(r[i], f.apply(a[i], b[i]), "(" + a[i] + ", " + b[i] + ") at index #" + i);
 482         }
 483     }
 484 
 485     static void assertArraysEquals(double[] r, double[] a, double b, FBinOp f) {
 486         int i = 0;
 487         try {
 488             for (; i < a.length; i++) {
 489                 Assert.assertEquals(r[i], f.apply(a[i], b));
 490             }
 491         } catch (AssertionError e) {
 492             Assert.assertEquals(r[i], f.apply(a[i], b), "(" + a[i] + ", " + b + ") at index #" + i);
 493         }
 494     }
 495 
 496     static void assertBroadcastArraysEquals(double[] r, double[] a, double[] b, FBinOp f) {
 497         int i = 0;
 498         try {
 499             for (; i < a.length; i++) {
 500                 Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()]));
 501             }
 502         } catch (AssertionError e) {
 503             Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()]),
 504                                 "(" + a[i] + ", " + b[(i / SPECIES.length()) * SPECIES.length()] + ") at index #" + i);
 505         }
 506     }
 507 
 508     static void assertBroadcastLongArraysEquals(double[] r, double[] a, double[] b, FBinOp f) {
 509         int i = 0;
 510         try {
 511             for (; i < a.length; i++) {
 512                 Assert.assertEquals(r[i], f.apply(a[i], (double)((long)b[(i / SPECIES.length()) * SPECIES.length()])));
 513             }
 514         } catch (AssertionError e) {
 515             Assert.assertEquals(r[i], f.apply(a[i], (double)((long)b[(i / SPECIES.length()) * SPECIES.length()])),
 516                                 "(" + a[i] + ", " + b[(i / SPECIES.length()) * SPECIES.length()] + ") at index #" + i);
 517         }
 518     }
 519 
 520     static void assertArraysEquals(double[] r, double[] a, double[] b, boolean[] mask, FBinOp f) {
 521         assertArraysEquals(r, a, b, mask, FBinMaskOp.lift(f));
 522     }
 523 
 524     static void assertArraysEquals(double[] r, double[] a, double[] b, boolean[] mask, FBinMaskOp f) {
 525         int i = 0;
 526         try {
 527             for (; i < a.length; i++) {
 528                 Assert.assertEquals(r[i], f.apply(a[i], b[i], mask[i % SPECIES.length()]));
 529             }
 530         } catch (AssertionError err) {
 531             Assert.assertEquals(r[i], f.apply(a[i], b[i], mask[i % SPECIES.length()]), "at index #" + i + ", input1 = " + a[i] + ", input2 = " + b[i] + ", mask = " + mask[i % SPECIES.length()]);
 532         }
 533     }
 534 
 535     static void assertArraysEquals(double[] r, double[] a, double b, boolean[] mask, FBinOp f) {
 536         assertArraysEquals(r, a, b, mask, FBinMaskOp.lift(f));
 537     }
 538 
 539     static void assertArraysEquals(double[] r, double[] a, double b, boolean[] mask, FBinMaskOp f) {
 540         int i = 0;
 541         try {
 542             for (; i < a.length; i++) {
 543                 Assert.assertEquals(r[i], f.apply(a[i], b, mask[i % SPECIES.length()]));
 544             }
 545         } catch (AssertionError err) {
 546             Assert.assertEquals(r[i], f.apply(a[i], b, mask[i % SPECIES.length()]), "at index #" + i + ", input1 = " + a[i] + ", input2 = " + b + ", mask = " + mask[i % SPECIES.length()]);
 547         }
 548     }
 549 
 550     static void assertBroadcastArraysEquals(double[] r, double[] a, double[] b, boolean[] mask, FBinOp f) {
 551         assertBroadcastArraysEquals(r, a, b, mask, FBinMaskOp.lift(f));
 552     }
 553 
 554     static void assertBroadcastArraysEquals(double[] r, double[] a, double[] b, boolean[] mask, FBinMaskOp f) {
 555         int i = 0;
 556         try {
 557             for (; i < a.length; i++) {
 558                 Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()], mask[i % SPECIES.length()]));
 559             }
 560         } catch (AssertionError err) {
 561             Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()],
 562                                 mask[i % SPECIES.length()]), "at index #" + i + ", input1 = " + a[i] +
 563                                 ", input2 = " + b[(i / SPECIES.length()) * SPECIES.length()] + ", mask = " +
 564                                 mask[i % SPECIES.length()]);
 565         }
 566     }
 567 
 568     static void assertBroadcastLongArraysEquals(double[] r, double[] a, double[] b, boolean[] mask, FBinOp f) {
 569         assertBroadcastLongArraysEquals(r, a, b, mask, FBinMaskOp.lift(f));
 570     }
 571 
 572     static void assertBroadcastLongArraysEquals(double[] r, double[] a, double[] b, boolean[] mask, FBinMaskOp f) {
 573         int i = 0;
 574         try {
 575             for (; i < a.length; i++) {
 576                 Assert.assertEquals(r[i], f.apply(a[i], (double)((long)b[(i / SPECIES.length()) * SPECIES.length()]), mask[i % SPECIES.length()]));
 577             }
 578         } catch (AssertionError err) {
 579             Assert.assertEquals(r[i], f.apply(a[i], (double)((long)b[(i / SPECIES.length()) * SPECIES.length()]),
 580                                 mask[i % SPECIES.length()]), "at index #" + i + ", input1 = " + a[i] +
 581                                 ", input2 = " + b[(i / SPECIES.length()) * SPECIES.length()] + ", mask = " +
 582                                 mask[i % SPECIES.length()]);
 583         }
 584     }
 585 
 586     static void assertShiftArraysEquals(double[] r, double[] a, double[] b, FBinOp f) {
 587         int i = 0;
 588         int j = 0;
 589         try {
 590             for (; j < a.length; j += SPECIES.length()) {
 591                 for (i = 0; i < SPECIES.length(); i++) {
 592                     Assert.assertEquals(r[i+j], f.apply(a[i+j], b[j]));
 593                 }
 594             }
 595         } catch (AssertionError e) {
 596             Assert.assertEquals(r[i+j], f.apply(a[i+j], b[j]), "at index #" + i + ", " + j);
 597         }
 598     }
 599 
 600     static void assertShiftArraysEquals(double[] r, double[] a, double[] b, boolean[] mask, FBinOp f) {
 601         assertShiftArraysEquals(r, a, b, mask, FBinMaskOp.lift(f));
 602     }
 603 
 604     static void assertShiftArraysEquals(double[] r, double[] a, double[] b, boolean[] mask, FBinMaskOp f) {
 605         int i = 0;
 606         int j = 0;
 607         try {
 608             for (; j < a.length; j += SPECIES.length()) {
 609                 for (i = 0; i < SPECIES.length(); i++) {
 610                     Assert.assertEquals(r[i+j], f.apply(a[i+j], b[j], mask[i]));
 611                 }
 612             }
 613         } catch (AssertionError err) {
 614             Assert.assertEquals(r[i+j], f.apply(a[i+j], b[j], mask[i]), "at index #" + i + ", input1 = " + a[i+j] + ", input2 = " + b[j] + ", mask = " + mask[i]);
 615         }
 616     }
 617 
 618     interface FBinConstOp {
 619         double apply(double a);
 620     }
 621 
 622     interface FBinConstMaskOp {
 623         double apply(double a, boolean m);
 624 
 625         static FBinConstMaskOp lift(FBinConstOp f) {
 626             return (a, m) -> m ? f.apply(a) : a;
 627         }
 628     }
 629 
 630     static void assertShiftConstEquals(double[] r, double[] a, FBinConstOp f) {
 631         int i = 0;
 632         int j = 0;
 633         try {
 634             for (; j < a.length; j += SPECIES.length()) {
 635                 for (i = 0; i < SPECIES.length(); i++) {
 636                     Assert.assertEquals(r[i+j], f.apply(a[i+j]));
 637                 }
 638             }
 639         } catch (AssertionError e) {
 640             Assert.assertEquals(r[i+j], f.apply(a[i+j]), "at index #" + i + ", " + j);
 641         }
 642     }
 643 
 644     static void assertShiftConstEquals(double[] r, double[] a, boolean[] mask, FBinConstOp f) {
 645         assertShiftConstEquals(r, a, mask, FBinConstMaskOp.lift(f));
 646     }
 647 
 648     static void assertShiftConstEquals(double[] r, double[] a, boolean[] mask, FBinConstMaskOp f) {
 649         int i = 0;
 650         int j = 0;
 651         try {
 652             for (; j < a.length; j += SPECIES.length()) {
 653                 for (i = 0; i < SPECIES.length(); i++) {
 654                     Assert.assertEquals(r[i+j], f.apply(a[i+j], mask[i]));
 655                 }
 656             }
 657         } catch (AssertionError err) {
 658             Assert.assertEquals(r[i+j], f.apply(a[i+j], mask[i]), "at index #" + i + ", input1 = " + a[i+j] + ", mask = " + mask[i]);
 659         }
 660     }
 661 
 662     interface FTernOp {
 663         double apply(double a, double b, double c);
 664     }
 665 
 666     interface FTernMaskOp {
 667         double apply(double a, double b, double c, boolean m);
 668 
 669         static FTernMaskOp lift(FTernOp f) {
 670             return (a, b, c, m) -> m ? f.apply(a, b, c) : a;
 671         }
 672     }
 673 
 674     static void assertArraysEquals(double[] r, double[] a, double[] b, double[] c, FTernOp f) {
 675         int i = 0;
 676         try {
 677             for (; i < a.length; i++) {
 678                 Assert.assertEquals(r[i], f.apply(a[i], b[i], c[i]));
 679             }
 680         } catch (AssertionError e) {
 681             Assert.assertEquals(r[i], f.apply(a[i], b[i], c[i]), "at index #" + i + ", input1 = " + a[i] + ", input2 = " + b[i] + ", input3 = " + c[i]);
 682         }
 683     }
 684 
 685     static void assertArraysEquals(double[] r, double[] a, double[] b, double[] c, boolean[] mask, FTernOp f) {
 686         assertArraysEquals(r, a, b, c, mask, FTernMaskOp.lift(f));
 687     }
 688 
 689     static void assertArraysEquals(double[] r, double[] a, double[] b, double[] c, boolean[] mask, FTernMaskOp f) {
 690         int i = 0;
 691         try {
 692             for (; i < a.length; i++) {
 693                 Assert.assertEquals(r[i], f.apply(a[i], b[i], c[i], mask[i % SPECIES.length()]));
 694             }
 695         } catch (AssertionError err) {
 696             Assert.assertEquals(r[i], f.apply(a[i], b[i], c[i], mask[i % SPECIES.length()]), "at index #" + i + ", input1 = " + a[i] + ", input2 = "
 697               + b[i] + ", input3 = " + c[i] + ", mask = " + mask[i % SPECIES.length()]);
 698         }
 699     }
 700 
 701     static void assertBroadcastArraysEquals(double[] r, double[] a, double[] b, double[] c, FTernOp f) {
 702         int i = 0;
 703         try {
 704             for (; i < a.length; i++) {
 705                 Assert.assertEquals(r[i], f.apply(a[i], b[i], c[(i / SPECIES.length()) * SPECIES.length()]));
 706             }
 707         } catch (AssertionError e) {
 708             Assert.assertEquals(r[i], f.apply(a[i], b[i], c[(i / SPECIES.length()) * SPECIES.length()]), "at index #" +
 709                                 i + ", input1 = " + a[i] + ", input2 = " + b[i] + ", input3 = " +
 710                                 c[(i / SPECIES.length()) * SPECIES.length()]);
 711         }
 712     }
 713 
 714     static void assertAltBroadcastArraysEquals(double[] r, double[] a, double[] b, double[] c, FTernOp f) {
 715         int i = 0;
 716         try {
 717             for (; i < a.length; i++) {
 718                 Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()], c[i]));
 719             }
 720         } catch (AssertionError e) {
 721             Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()], c[i]), "at index #" +
 722                                 i + ", input1 = " + a[i] + ", input2 = " +
 723                                 b[(i / SPECIES.length()) * SPECIES.length()] + ",  input3 = " + c[i]);
 724         }
 725     }
 726 
 727     static void assertBroadcastArraysEquals(double[] r, double[] a, double[] b, double[] c, boolean[] mask,
 728                                             FTernOp f) {
 729         assertBroadcastArraysEquals(r, a, b, c, mask, FTernMaskOp.lift(f));
 730     }
 731 
 732     static void assertBroadcastArraysEquals(double[] r, double[] a, double[] b, double[] c, boolean[] mask,
 733                                             FTernMaskOp f) {
 734         int i = 0;
 735         try {
 736             for (; i < a.length; i++) {
 737                 Assert.assertEquals(r[i], f.apply(a[i], b[i], c[(i / SPECIES.length()) * SPECIES.length()],
 738                                     mask[i % SPECIES.length()]));
 739             }
 740         } catch (AssertionError err) {
 741             Assert.assertEquals(r[i], f.apply(a[i], b[i], c[(i / SPECIES.length()) * SPECIES.length()],
 742                                 mask[i % SPECIES.length()]), "at index #" + i + ", input1 = " + a[i] + ", input2 = " +
 743                                 b[i] + ", input3 = " + c[(i / SPECIES.length()) * SPECIES.length()] + ", mask = " +
 744                                 mask[i % SPECIES.length()]);
 745         }
 746     }
 747 
 748     static void assertAltBroadcastArraysEquals(double[] r, double[] a, double[] b, double[] c, boolean[] mask,
 749                                             FTernOp f) {
 750         assertAltBroadcastArraysEquals(r, a, b, c, mask, FTernMaskOp.lift(f));
 751     }
 752 
 753     static void assertAltBroadcastArraysEquals(double[] r, double[] a, double[] b, double[] c, boolean[] mask,
 754                                             FTernMaskOp f) {
 755         int i = 0;
 756         try {
 757             for (; i < a.length; i++) {
 758                 Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()], c[i],
 759                                     mask[i % SPECIES.length()]));
 760             }
 761         } catch (AssertionError err) {
 762             Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()], c[i],
 763                                 mask[i % SPECIES.length()]), "at index #" + i + ", input1 = " + a[i] +
 764                                 ", input2 = " + b[(i / SPECIES.length()) * SPECIES.length()] +
 765                                 ", input3 = " + c[i] + ", mask = " + mask[i % SPECIES.length()]);
 766         }
 767     }
 768 
 769     static void assertDoubleBroadcastArraysEquals(double[] r, double[] a, double[] b, double[] c, FTernOp f) {
 770         int i = 0;
 771         try {
 772             for (; i < a.length; i++) {
 773                 Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()],
 774                                     c[(i / SPECIES.length()) * SPECIES.length()]));
 775             }
 776         } catch (AssertionError e) {
 777             Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()],
 778                                 c[(i / SPECIES.length()) * SPECIES.length()]), "at index #" + i + ", input1 = " + a[i]
 779                                 + ", input2 = " + b[(i / SPECIES.length()) * SPECIES.length()] + ", input3 = " +
 780                                 c[(i / SPECIES.length()) * SPECIES.length()]);
 781         }
 782     }
 783 
 784     static void assertDoubleBroadcastArraysEquals(double[] r, double[] a, double[] b, double[] c, boolean[] mask,
 785                                                   FTernOp f) {
 786         assertDoubleBroadcastArraysEquals(r, a, b, c, mask, FTernMaskOp.lift(f));
 787     }
 788 
 789     static void assertDoubleBroadcastArraysEquals(double[] r, double[] a, double[] b, double[] c, boolean[] mask,
 790                                                   FTernMaskOp f) {
 791         int i = 0;
 792         try {
 793             for (; i < a.length; i++) {
 794                 Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()],
 795                                     c[(i / SPECIES.length()) * SPECIES.length()], mask[i % SPECIES.length()]));
 796             }
 797         } catch (AssertionError err) {
 798             Assert.assertEquals(r[i], f.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()],
 799                                 c[(i / SPECIES.length()) * SPECIES.length()], mask[i % SPECIES.length()]), "at index #"
 800                                 + i + ", input1 = " + a[i] + ", input2 = " + b[(i / SPECIES.length()) * SPECIES.length()] +
 801                                 ", input3 = " + c[(i / SPECIES.length()) * SPECIES.length()] + ", mask = " +
 802                                 mask[i % SPECIES.length()]);
 803         }
 804     }
 805 
 806 
 807     static boolean isWithin1Ulp(double actual, double expected) {
 808         if (Double.isNaN(expected) && !Double.isNaN(actual)) {
 809             return false;
 810         } else if (!Double.isNaN(expected) && Double.isNaN(actual)) {
 811             return false;
 812         }
 813 
 814         double low = Math.nextDown(expected);
 815         double high = Math.nextUp(expected);
 816 
 817         if (Double.compare(low, expected) > 0) {
 818             return false;
 819         }
 820 
 821         if (Double.compare(high, expected) < 0) {
 822             return false;
 823         }
 824 
 825         return true;
 826     }
 827 
 828     static void assertArraysEqualsWithinOneUlp(double[] r, double[] a, FUnOp mathf, FUnOp strictmathf) {
 829         int i = 0;
 830         try {
 831             // Check that result is within 1 ulp of strict math or equivalent to math implementation.
 832             for (; i < a.length; i++) {
 833                 Assert.assertTrue(Double.compare(r[i], mathf.apply(a[i])) == 0 ||
 834                                     isWithin1Ulp(r[i], strictmathf.apply(a[i])));
 835             }
 836         } catch (AssertionError e) {
 837             Assert.assertTrue(Double.compare(r[i], mathf.apply(a[i])) == 0, "at index #" + i + ", input = " + a[i] + ", actual = " + r[i] + ", expected = " + mathf.apply(a[i]));
 838             Assert.assertTrue(isWithin1Ulp(r[i], strictmathf.apply(a[i])), "at index #" + i + ", input = " + a[i] + ", actual = " + r[i] + ", expected (within 1 ulp) = " + strictmathf.apply(a[i]));
 839         }
 840     }
 841 
 842     static void assertArraysEqualsWithinOneUlp(double[] r, double[] a, double[] b, FBinOp mathf, FBinOp strictmathf) {
 843         int i = 0;
 844         try {
 845             // Check that result is within 1 ulp of strict math or equivalent to math implementation.
 846             for (; i < a.length; i++) {
 847                 Assert.assertTrue(Double.compare(r[i], mathf.apply(a[i], b[i])) == 0 ||
 848                                     isWithin1Ulp(r[i], strictmathf.apply(a[i], b[i])));
 849             }
 850         } catch (AssertionError e) {
 851             Assert.assertTrue(Double.compare(r[i], mathf.apply(a[i], b[i])) == 0, "at index #" + i + ", input1 = " + a[i] + ", input2 = " + b[i] + ", actual = " + r[i] + ", expected = " + mathf.apply(a[i], b[i]));
 852             Assert.assertTrue(isWithin1Ulp(r[i], strictmathf.apply(a[i], b[i])), "at index #" + i + ", input1 = " + a[i] + ", input2 = " + b[i] + ", actual = " + r[i] + ", expected (within 1 ulp) = " + strictmathf.apply(a[i], b[i]));
 853         }
 854     }
 855 
 856     static void assertBroadcastArraysEqualsWithinOneUlp(double[] r, double[] a, double[] b,
 857                                                         FBinOp mathf, FBinOp strictmathf) {
 858         int i = 0;
 859         try {
 860             // Check that result is within 1 ulp of strict math or equivalent to math implementation.
 861             for (; i < a.length; i++) {
 862                 Assert.assertTrue(Double.compare(r[i],
 863                                   mathf.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()])) == 0 ||
 864                                   isWithin1Ulp(r[i],
 865                                   strictmathf.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()])));
 866             }
 867         } catch (AssertionError e) {
 868             Assert.assertTrue(Double.compare(r[i],
 869                               mathf.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()])) == 0,
 870                               "at index #" + i + ", input1 = " + a[i] + ", input2 = " +
 871                               b[(i / SPECIES.length()) * SPECIES.length()] + ", actual = " + r[i] +
 872                               ", expected = " + mathf.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()]));
 873             Assert.assertTrue(isWithin1Ulp(r[i],
 874                               strictmathf.apply(a[i], b[(i / SPECIES.length()) * SPECIES.length()])),
 875                              "at index #" + i + ", input1 = " + a[i] + ", input2 = " +
 876                              b[(i / SPECIES.length()) * SPECIES.length()] + ", actual = " + r[i] +
 877                              ", expected (within 1 ulp) = " + strictmathf.apply(a[i],
 878                              b[(i / SPECIES.length()) * SPECIES.length()]));
 879         }
 880     }
 881 
 882     interface FGatherScatterOp {
 883         double[] apply(double[] a, int ix, int[] b, int iy);
 884     }
 885 
 886     static void assertArraysEquals(double[] r, double[] a, int[] b, FGatherScatterOp f) {
 887         int i = 0;
 888         try {
 889             for (; i < a.length; i += SPECIES.length()) {
 890                 Assert.assertEquals(Arrays.copyOfRange(r, i, i+SPECIES.length()),
 891                   f.apply(a, i, b, i));
 892             }
 893         } catch (AssertionError e) {
 894             double[] ref = f.apply(a, i, b, i);
 895             double[] res = Arrays.copyOfRange(r, i, i+SPECIES.length());
 896             Assert.assertEquals(res, ref,
 897               "(ref: " + Arrays.toString(ref) + ", res: " + Arrays.toString(res) + ", a: "
 898               + Arrays.toString(Arrays.copyOfRange(a, i, i+SPECIES.length()))
 899               + ", b: "
 900               + Arrays.toString(Arrays.copyOfRange(b, i, i+SPECIES.length()))
 901               + " at index #" + i);
 902         }
 903     }
 904 
 905     interface FGatherMaskedOp {
 906         double[] apply(double[] a, int ix, boolean[] mask, int[] b, int iy);
 907     }
 908 
 909     interface FScatterMaskedOp {
 910         double[] apply(double[] r, double[] a, int ix, boolean[] mask, int[] b, int iy);
 911     }
 912 
 913     static void assertArraysEquals(double[] r, double[] a, int[] b, boolean[] mask, FGatherMaskedOp f) {
 914         int i = 0;
 915         try {
 916             for (; i < a.length; i += SPECIES.length()) {
 917                 Assert.assertEquals(Arrays.copyOfRange(r, i, i+SPECIES.length()),
 918                   f.apply(a, i, mask, b, i));
 919             }
 920         } catch (AssertionError e) {
 921             double[] ref = f.apply(a, i, mask, b, i);
 922             double[] res = Arrays.copyOfRange(r, i, i+SPECIES.length());
 923             Assert.assertEquals(res, ref,
 924               "(ref: " + Arrays.toString(ref) + ", res: " + Arrays.toString(res) + ", a: "
 925               + Arrays.toString(Arrays.copyOfRange(a, i, i+SPECIES.length()))
 926               + ", b: "
 927               + Arrays.toString(Arrays.copyOfRange(b, i, i+SPECIES.length()))
 928               + ", mask: "
 929               + Arrays.toString(mask)
 930               + " at index #" + i);
 931         }
 932     }
 933 
 934     static void assertArraysEquals(double[] r, double[] a, int[] b, boolean[] mask, FScatterMaskedOp f) {
 935         int i = 0;
 936         try {
 937             for (; i < a.length; i += SPECIES.length()) {
 938                 Assert.assertEquals(Arrays.copyOfRange(r, i, i+SPECIES.length()),
 939                   f.apply(r, a, i, mask, b, i));
 940             }
 941         } catch (AssertionError e) {
 942             double[] ref = f.apply(r, a, i, mask, b, i);
 943             double[] res = Arrays.copyOfRange(r, i, i+SPECIES.length());
 944             Assert.assertEquals(res, ref,
 945               "(ref: " + Arrays.toString(ref) + ", res: " + Arrays.toString(res) + ", a: "
 946               + Arrays.toString(Arrays.copyOfRange(a, i, i+SPECIES.length()))
 947               + ", b: "
 948               + Arrays.toString(Arrays.copyOfRange(b, i, i+SPECIES.length()))
 949               + ", r: "
 950               + Arrays.toString(Arrays.copyOfRange(r, i, i+SPECIES.length()))
 951               + ", mask: "
 952               + Arrays.toString(mask)
 953               + " at index #" + i);
 954         }
 955     }
 956 
 957     interface FLaneOp {
 958         double[] apply(double[] a, int origin, int idx);
 959     }
 960 
 961     static void assertArraysEquals(double[] r, double[] a, int origin, FLaneOp f) {
 962         int i = 0;
 963         try {
 964             for (; i < a.length; i += SPECIES.length()) {
 965                 Assert.assertEquals(Arrays.copyOfRange(r, i, i+SPECIES.length()),
 966                   f.apply(a, origin, i));
 967             }
 968         } catch (AssertionError e) {
 969             double[] ref = f.apply(a, origin, i);
 970             double[] res = Arrays.copyOfRange(r, i, i+SPECIES.length());
 971             Assert.assertEquals(res, ref, "(ref: " + Arrays.toString(ref)
 972               + ", res: " + Arrays.toString(res)
 973               + "), at index #" + i);
 974         }
 975     }
 976 
 977     interface FLaneBop {
 978         double[] apply(double[] a, double[] b, int origin, int idx);
 979     }
 980 
 981     static void assertArraysEquals(double[] r, double[] a, double[] b, int origin, FLaneBop f) {
 982         int i = 0;
 983         try {
 984             for (; i < a.length; i += SPECIES.length()) {
 985                 Assert.assertEquals(Arrays.copyOfRange(r, i, i+SPECIES.length()),
 986                   f.apply(a, b, origin, i));
 987             }
 988         } catch (AssertionError e) {
 989             double[] ref = f.apply(a, b, origin, i);
 990             double[] res = Arrays.copyOfRange(r, i, i+SPECIES.length());
 991             Assert.assertEquals(res, ref, "(ref: " + Arrays.toString(ref)
 992               + ", res: " + Arrays.toString(res)
 993               + "), at index #" + i
 994               + ", at origin #" + origin);
 995         }
 996     }
 997 
 998     interface FLaneMaskedBop {
 999         double[] apply(double[] a, double[] b, int origin, boolean[] mask, int idx);
1000     }
1001 
1002     static void assertArraysEquals(double[] r, double[] a, double[] b, int origin, boolean[] mask, FLaneMaskedBop f) {
1003         int i = 0;
1004         try {
1005             for (; i < a.length; i += SPECIES.length()) {
1006                 Assert.assertEquals(Arrays.copyOfRange(r, i, i+SPECIES.length()),
1007                   f.apply(a, b, origin, mask, i));
1008             }
1009         } catch (AssertionError e) {
1010             double[] ref = f.apply(a, b, origin, mask, i);
1011             double[] res = Arrays.copyOfRange(r, i, i+SPECIES.length());
1012             Assert.assertEquals(res, ref, "(ref: " + Arrays.toString(ref)
1013               + ", res: " + Arrays.toString(res)
1014               + "), at index #" + i
1015               + ", at origin #" + origin);
1016         }
1017     }
1018 
1019     interface FLanePartBop {
1020         double[] apply(double[] a, double[] b, int origin, int part, int idx);
1021     }
1022 
1023     static void assertArraysEquals(double[] r, double[] a, double[] b, int origin, int part, FLanePartBop f) {
1024         int i = 0;
1025         try {
1026             for (; i < a.length; i += SPECIES.length()) {
1027                 Assert.assertEquals(Arrays.copyOfRange(r, i, i+SPECIES.length()),
1028                   f.apply(a, b, origin, part, i));
1029             }
1030         } catch (AssertionError e) {
1031             double[] ref = f.apply(a, b, origin, part, i);
1032             double[] res = Arrays.copyOfRange(r, i, i+SPECIES.length());
1033             Assert.assertEquals(res, ref, "(ref: " + Arrays.toString(ref)
1034               + ", res: " + Arrays.toString(res)
1035               + "), at index #" + i
1036               + ", at origin #" + origin
1037               + ", with part #" + part);
1038         }
1039     }
1040 
1041     interface FLanePartMaskedBop {
1042         double[] apply(double[] a, double[] b, int origin, int part, boolean[] mask, int idx);
1043     }
1044 
1045     static void assertArraysEquals(double[] r, double[] a, double[] b, int origin, int part, boolean[] mask, FLanePartMaskedBop f) {
1046         int i = 0;
1047         try {
1048             for (; i < a.length; i += SPECIES.length()) {
1049                 Assert.assertEquals(Arrays.copyOfRange(r, i, i+SPECIES.length()),
1050                   f.apply(a, b, origin, part, mask, i));
1051             }
1052         } catch (AssertionError e) {
1053             double[] ref = f.apply(a, b, origin, part, mask, i);
1054             double[] res = Arrays.copyOfRange(r, i, i+SPECIES.length());
1055             Assert.assertEquals(res, ref, "(ref: " + Arrays.toString(ref)
1056               + ", res: " + Arrays.toString(res)
1057               + "), at index #" + i
1058               + ", at origin #" + origin
1059               + ", with part #" + part);
1060         }
1061     }
1062 
1063     static int intCornerCaseValue(int i) {
1064         switch(i % 5) {
1065             case 0:
1066                 return Integer.MAX_VALUE;
1067             case 1:
1068                 return Integer.MIN_VALUE;
1069             case 2:
1070                 return Integer.MIN_VALUE;
1071             case 3:
1072                 return Integer.MAX_VALUE;
1073             default:
1074                 return (int)0;
1075         }
1076     }
1077 
1078     static final List<IntFunction<double[]>> INT_DOUBLE_GENERATORS = List.of(
1079             withToString("double[-i * 5]", (int s) -> {
1080                 return fill(s * BUFFER_REPS,
1081                             i -> (double)(-i * 5));
1082             }),
1083             withToString("double[i * 5]", (int s) -> {
1084                 return fill(s * BUFFER_REPS,
1085                             i -> (double)(i * 5));
1086             }),
1087             withToString("double[i + 1]", (int s) -> {
1088                 return fill(s * BUFFER_REPS,
1089                             i -> (((double)(i + 1) == 0) ? 1 : (double)(i + 1)));
1090             }),
1091             withToString("double[intCornerCaseValue(i)]", (int s) -> {
1092                 return fill(s * BUFFER_REPS,
1093                             i -> (double)intCornerCaseValue(i));
1094             })
1095     );
1096 
1097     static void assertArraysEquals(int[] r, double[] a, int offs) {
1098         int i = 0;
1099         try {
1100             for (; i < r.length; i++) {
1101                 Assert.assertEquals(r[i], (int)(a[i+offs]));
1102             }
1103         } catch (AssertionError e) {
1104             Assert.assertEquals(r[i], (int)(a[i+offs]), "at index #" + i + ", input = " + a[i+offs]);
1105         }
1106     }
1107 
1108     static long longCornerCaseValue(int i) {
1109         switch(i % 5) {
1110             case 0:
1111                 return Long.MAX_VALUE;
1112             case 1:
1113                 return Long.MIN_VALUE;
1114             case 2:
1115                 return Long.MIN_VALUE;
1116             case 3:
1117                 return Long.MAX_VALUE;
1118             default:
1119                 return (long)0;
1120         }
1121     }
1122 
1123     static final List<IntFunction<double[]>> LONG_DOUBLE_GENERATORS = List.of(
1124             withToString("double[-i * 5]", (int s) -> {
1125                 return fill(s * BUFFER_REPS,
1126                             i -> (double)(-i * 5));
1127             }),
1128             withToString("double[i * 5]", (int s) -> {
1129                 return fill(s * BUFFER_REPS,
1130                             i -> (double)(i * 5));
1131             }),
1132             withToString("double[i + 1]", (int s) -> {
1133                 return fill(s * BUFFER_REPS,
1134                             i -> (((double)(i + 1) == 0) ? 1 : (double)(i + 1)));
1135             }),
1136             withToString("double[cornerCaseValue(i)]", (int s) -> {
1137                 return fill(s * BUFFER_REPS,
1138                             i -> (double)longCornerCaseValue(i));
1139             })
1140     );
1141 
1142 
1143     static void assertArraysEquals(long[] r, double[] a, int offs) {
1144         int i = 0;
1145         try {
1146             for (; i < r.length; i++) {
1147                 Assert.assertEquals(r[i], (long)(a[i+offs]));
1148             }
1149         } catch (AssertionError e) {
1150             Assert.assertEquals(r[i], (long)(a[i+offs]), "at index #" + i + ", input = " + a[i+offs]);
1151         }
1152     }
1153 
1154     static long bits(double e) {
1155         return  Double.doubleToLongBits(e);
1156     }
1157 
1158     static final List<IntFunction<double[]>> DOUBLE_GENERATORS = List.of(
1159             withToString("double[-i * 5]", (int s) -> {
1160                 return fill(s * BUFFER_REPS,
1161                             i -> (double)(-i * 5));
1162             }),
1163             withToString("double[i * 5]", (int s) -> {
1164                 return fill(s * BUFFER_REPS,
1165                             i -> (double)(i * 5));
1166             }),
1167             withToString("double[i + 1]", (int s) -> {
1168                 return fill(s * BUFFER_REPS,
1169                             i -> (((double)(i + 1) == 0) ? 1 : (double)(i + 1)));
1170             }),
1171             withToString("double[0.01 + (i / (i + 1))]", (int s) -> {
1172                 return fill(s * BUFFER_REPS,
1173                             i -> (double)0.01 + ((double)i / (i + 1)));
1174             }),
1175             withToString("double[i -> i % 17 == 0 ? cornerCaseValue(i) : 0.01 + (i / (i + 1))]", (int s) -> {
1176                 return fill(s * BUFFER_REPS,
1177                             i -> i % 17 == 0 ? cornerCaseValue(i) : (double)0.01 + ((double)i / (i + 1)));
1178             }),
1179             withToString("double[cornerCaseValue(i)]", (int s) -> {
1180                 return fill(s * BUFFER_REPS,
1181                             i -> cornerCaseValue(i));
1182             })
1183     );
1184 
1185     // Create combinations of pairs
1186     // @@@ Might be sensitive to order e.g. div by 0
1187     static final List<List<IntFunction<double[]>>> DOUBLE_GENERATOR_PAIRS =
1188         Stream.of(DOUBLE_GENERATORS.get(0)).
1189                 flatMap(fa -> DOUBLE_GENERATORS.stream().skip(1).map(fb -> List.of(fa, fb))).
1190                 collect(Collectors.toList());
1191 
1192     @DataProvider
1193     public Object[][] boolUnaryOpProvider() {
1194         return BOOL_ARRAY_GENERATORS.stream().
1195                 map(f -> new Object[]{f}).
1196                 toArray(Object[][]::new);
1197     }
1198 
1199     static final List<List<IntFunction<double[]>>> DOUBLE_GENERATOR_TRIPLES =
1200         DOUBLE_GENERATOR_PAIRS.stream().
1201                 flatMap(pair -> DOUBLE_GENERATORS.stream().map(f -> List.of(pair.get(0), pair.get(1), f))).
1202                 collect(Collectors.toList());
1203 
1204     static final List<IntFunction<double[]>> SELECT_FROM_INDEX_GENERATORS = List.of(
1205             withToString("double[0..VECLEN*2)", (int s) -> {
1206                 return fill(s * BUFFER_REPS,
1207                             i -> (double)(RAND.nextInt()));
1208             })
1209     );
1210 
1211     static final List<List<IntFunction<double[]>>> DOUBLE_GENERATOR_SELECT_FROM_TRIPLES =
1212         DOUBLE_GENERATOR_PAIRS.stream().
1213                 flatMap(pair -> SELECT_FROM_INDEX_GENERATORS.stream().map(f -> List.of(pair.get(0), pair.get(1), f))).
1214                 collect(Collectors.toList());
1215 
1216     @DataProvider
1217     public Object[][] doubleBinaryOpProvider() {
1218         return DOUBLE_GENERATOR_PAIRS.stream().map(List::toArray).
1219                 toArray(Object[][]::new);
1220     }
1221 
1222     @DataProvider
1223     public Object[][] doubleIndexedOpProvider() {
1224         return DOUBLE_GENERATOR_PAIRS.stream().map(List::toArray).
1225                 toArray(Object[][]::new);
1226     }
1227 
1228     @DataProvider
1229     public Object[][] doubleBinaryOpMaskProvider() {
1230         return BOOLEAN_MASK_GENERATORS.stream().
1231                 flatMap(fm -> DOUBLE_GENERATOR_PAIRS.stream().map(lfa -> {
1232                     return Stream.concat(lfa.stream(), Stream.of(fm)).toArray();
1233                 })).
1234                 toArray(Object[][]::new);
1235     }
1236 
1237     @DataProvider
1238     public Object[][] doubleTernaryOpProvider() {
1239         return DOUBLE_GENERATOR_TRIPLES.stream().map(List::toArray).
1240                 toArray(Object[][]::new);
1241     }
1242 
1243     @DataProvider
1244     public Object[][] doubleSelectFromTwoVectorOpProvider() {
1245         return DOUBLE_GENERATOR_SELECT_FROM_TRIPLES.stream().map(List::toArray).
1246                 toArray(Object[][]::new);
1247     }
1248 
1249     @DataProvider
1250     public Object[][] doubleTernaryOpMaskProvider() {
1251         return BOOLEAN_MASK_GENERATORS.stream().
1252                 flatMap(fm -> DOUBLE_GENERATOR_TRIPLES.stream().map(lfa -> {
1253                     return Stream.concat(lfa.stream(), Stream.of(fm)).toArray();
1254                 })).
1255                 toArray(Object[][]::new);
1256     }
1257 
1258     @DataProvider
1259     public Object[][] doubleUnaryOpProvider() {
1260         return DOUBLE_GENERATORS.stream().
1261                 map(f -> new Object[]{f}).
1262                 toArray(Object[][]::new);
1263     }
1264 
1265     @DataProvider
1266     public Object[][] doubleUnaryOpMaskProvider() {
1267         return BOOLEAN_MASK_GENERATORS.stream().
1268                 flatMap(fm -> DOUBLE_GENERATORS.stream().map(fa -> {
1269                     return new Object[] {fa, fm};
1270                 })).
1271                 toArray(Object[][]::new);
1272     }
1273 
1274     @DataProvider
1275     public Object[][] doubletoIntUnaryOpProvider() {
1276         return INT_DOUBLE_GENERATORS.stream().
1277                 map(f -> new Object[]{f}).
1278                 toArray(Object[][]::new);
1279     }
1280 
1281     @DataProvider
1282     public Object[][] doubletoLongUnaryOpProvider() {
1283         return LONG_DOUBLE_GENERATORS.stream().
1284                 map(f -> new Object[]{f}).
1285                 toArray(Object[][]::new);
1286     }
1287 
1288     @DataProvider
1289     public Object[][] maskProvider() {
1290         return BOOLEAN_MASK_GENERATORS.stream().
1291                 map(f -> new Object[]{f}).
1292                 toArray(Object[][]::new);
1293     }
1294 
1295     @DataProvider
1296     public Object[][] maskCompareOpProvider() {
1297         return BOOLEAN_MASK_COMPARE_GENERATOR_PAIRS.stream().map(List::toArray).
1298                 toArray(Object[][]::new);
1299     }
1300 
1301     @DataProvider
1302     public Object[][] shuffleProvider() {
1303         return INT_SHUFFLE_GENERATORS.stream().
1304                 map(f -> new Object[]{f}).
1305                 toArray(Object[][]::new);
1306     }
1307 
1308     @DataProvider
1309     public Object[][] shuffleCompareOpProvider() {
1310         return INT_SHUFFLE_COMPARE_GENERATOR_PAIRS.stream().map(List::toArray).
1311                 toArray(Object[][]::new);
1312     }
1313 
1314     @DataProvider
1315     public Object[][] doubleUnaryOpShuffleProvider() {
1316         return INT_SHUFFLE_GENERATORS.stream().
1317                 flatMap(fs -> DOUBLE_GENERATORS.stream().map(fa -> {
1318                     return new Object[] {fa, fs};
1319                 })).
1320                 toArray(Object[][]::new);
1321     }
1322 
1323     @DataProvider
1324     public Object[][] doubleUnaryOpShuffleMaskProvider() {
1325         return BOOLEAN_MASK_GENERATORS.stream().
1326                 flatMap(fm -> INT_SHUFFLE_GENERATORS.stream().
1327                     flatMap(fs -> DOUBLE_GENERATORS.stream().map(fa -> {
1328                         return new Object[] {fa, fs, fm};
1329                 }))).
1330                 toArray(Object[][]::new);
1331     }
1332 
1333     static final List<BiFunction<Integer,Integer,double[]>> DOUBLE_SHUFFLE_GENERATORS = List.of(
1334             withToStringBi("shuffle[random]", (Integer l, Integer m) -> {
1335                 double[] a = new double[l];
1336                 int upper = m;
1337                 for (int i = 0; i < 1; i++) {
1338                     a[i] = (double)RAND.nextInt(upper);
1339                 }
1340                 return a;
1341             })
1342     );
1343 
1344     @DataProvider
1345     public Object[][] doubleUnaryOpSelectFromProvider() {
1346         return DOUBLE_SHUFFLE_GENERATORS.stream().
1347                 flatMap(fs -> DOUBLE_GENERATORS.stream().map(fa -> {
1348                     return new Object[] {fa, fs};
1349                 })).
1350                 toArray(Object[][]::new);
1351     }
1352 
1353     @DataProvider
1354     public Object[][] doubleUnaryOpSelectFromMaskProvider() {
1355         return BOOLEAN_MASK_GENERATORS.stream().
1356                 flatMap(fm -> DOUBLE_SHUFFLE_GENERATORS.stream().
1357                     flatMap(fs -> DOUBLE_GENERATORS.stream().map(fa -> {
1358                         return new Object[] {fa, fs, fm};
1359                 }))).
1360                 toArray(Object[][]::new);
1361     }
1362 
1363     static final List<IntFunction<double[]>> DOUBLE_COMPARE_GENERATORS = List.of(
1364             withToString("double[i]", (int s) -> {
1365                 return fill(s * BUFFER_REPS,
1366                             i -> (double)i);
1367             }),
1368             withToString("double[i - length / 2]", (int s) -> {
1369                 return fill(s * BUFFER_REPS,
1370                             i -> (double)(i - (s * BUFFER_REPS / 2)));
1371             }),
1372             withToString("double[i + 1]", (int s) -> {
1373                 return fill(s * BUFFER_REPS,
1374                             i -> (double)(i + 1));
1375             }),
1376             withToString("double[i - 2]", (int s) -> {
1377                 return fill(s * BUFFER_REPS,
1378                             i -> (double)(i - 2));
1379             }),
1380             withToString("double[zigZag(i)]", (int s) -> {
1381                 return fill(s * BUFFER_REPS,
1382                             i -> i%3 == 0 ? (double)i : (i%3 == 1 ? (double)(i + 1) : (double)(i - 2)));
1383             }),
1384             withToString("double[cornerCaseValue(i)]", (int s) -> {
1385                 return fill(s * BUFFER_REPS,
1386                             i -> cornerCaseValue(i));
1387             })
1388     );
1389 
1390     static final List<List<IntFunction<double[]>>> DOUBLE_TEST_GENERATOR_ARGS =
1391         DOUBLE_COMPARE_GENERATORS.stream().
1392                 map(fa -> List.of(fa)).
1393                 collect(Collectors.toList());
1394 
1395     @DataProvider
1396     public Object[][] doubleTestOpProvider() {
1397         return DOUBLE_TEST_GENERATOR_ARGS.stream().map(List::toArray).
1398                 toArray(Object[][]::new);
1399     }
1400 
1401     @DataProvider
1402     public Object[][] doubleTestOpMaskProvider() {
1403         return BOOLEAN_MASK_GENERATORS.stream().
1404                 flatMap(fm -> DOUBLE_TEST_GENERATOR_ARGS.stream().map(lfa -> {
1405                     return Stream.concat(lfa.stream(), Stream.of(fm)).toArray();
1406                 })).
1407                 toArray(Object[][]::new);
1408     }
1409 
1410     static final List<List<IntFunction<double[]>>> DOUBLE_COMPARE_GENERATOR_PAIRS =
1411         DOUBLE_COMPARE_GENERATORS.stream().
1412                 flatMap(fa -> DOUBLE_COMPARE_GENERATORS.stream().map(fb -> List.of(fa, fb))).
1413                 collect(Collectors.toList());
1414 
1415     @DataProvider
1416     public Object[][] doubleCompareOpProvider() {
1417         return DOUBLE_COMPARE_GENERATOR_PAIRS.stream().map(List::toArray).
1418                 toArray(Object[][]::new);
1419     }
1420 
1421     @DataProvider
1422     public Object[][] doubleCompareOpMaskProvider() {
1423         return BOOLEAN_MASK_GENERATORS.stream().
1424                 flatMap(fm -> DOUBLE_COMPARE_GENERATOR_PAIRS.stream().map(lfa -> {
1425                     return Stream.concat(lfa.stream(), Stream.of(fm)).toArray();
1426                 })).
1427                 toArray(Object[][]::new);
1428     }
1429 
1430     interface ToDoubleF {
1431         double apply(int i);
1432     }
1433 
1434     static double[] fill(int s , ToDoubleF f) {
1435         return fill(new double[s], f);
1436     }
1437 
1438     static double[] fill(double[] a, ToDoubleF f) {
1439         for (int i = 0; i < a.length; i++) {
1440             a[i] = f.apply(i);
1441         }
1442         return a;
1443     }
1444 
1445     static double cornerCaseValue(int i) {
1446         return switch(i % 8) {
1447             case 0  -> Double.MAX_VALUE;
1448             case 1  -> Double.MIN_VALUE;
1449             case 2  -> Double.NEGATIVE_INFINITY;
1450             case 3  -> Double.POSITIVE_INFINITY;
1451             case 4  -> Double.NaN;
1452             case 5  -> Double.longBitsToDouble(0x7FF123456789ABCDL);
1453             case 6  -> (double)0.0;
1454             default -> (double)-0.0;
1455         };
1456     }
1457 
1458     static final IntFunction<double[]> fr = (vl) -> {
1459         int length = BUFFER_REPS * vl;
1460         return new double[length];
1461     };
1462 
1463     static final IntFunction<boolean[]> fmr = (vl) -> {
1464         int length = BUFFER_REPS * vl;
1465         return new boolean[length];
1466     };
1467 
1468     static final IntFunction<long[]> lfr = (vl) -> {
1469         int length = BUFFER_REPS * vl;
1470         return new long[length];
1471     };
1472 
1473     static boolean eq(double a, double b) {
1474         return a == b;
1475     }
1476 
1477     static boolean neq(double a, double b) {
1478         return a != b;
1479     }
1480 
1481     static boolean lt(double a, double b) {
1482         return a < b;
1483     }
1484 
1485     static boolean le(double a, double b) {
1486         return a <= b;
1487     }
1488 
1489     static boolean gt(double a, double b) {
1490         return a > b;
1491     }
1492 
1493     static boolean ge(double a, double b) {
1494         return a >= b;
1495     }
1496 
1497     static double firstNonZero(double a, double b) {
1498         return Double.compare(a, (double) 0) != 0 ? a : b;
1499     }
1500 
1501     @Test
1502     static void smokeTest1() {
1503         DoubleVector three = DoubleVector.broadcast(SPECIES, (byte)-3);
1504         DoubleVector three2 = (DoubleVector) SPECIES.broadcast(-3);
1505         assert(three.eq(three2).allTrue());
1506         DoubleVector three3 = three2.broadcast(1).broadcast(-3);
1507         assert(three.eq(three3).allTrue());
1508         int scale = 2;
1509         Class<?> ETYPE = double.class;
1510         if (ETYPE == double.class || ETYPE == long.class)
1511             scale = 1000000;
1512         else if (ETYPE == byte.class && SPECIES.length() >= 64)
1513             scale = 1;
1514         DoubleVector higher = three.addIndex(scale);
1515         VectorMask<Double> m = three.compare(VectorOperators.LE, higher);
1516         assert(m.allTrue());
1517         m = higher.min((double)-1).test(VectorOperators.IS_NEGATIVE);
1518         assert(m.allTrue());
1519         m = higher.test(VectorOperators.IS_FINITE);
1520         assert(m.allTrue());
1521         double max = higher.reduceLanes(VectorOperators.MAX);
1522         assert(max == -3 + scale * (SPECIES.length()-1));
1523     }
1524 
1525     private static double[]
1526     bothToArray(DoubleVector a, DoubleVector b) {
1527         double[] r = new double[a.length() + b.length()];
1528         a.intoArray(r, 0);
1529         b.intoArray(r, a.length());
1530         return r;
1531     }
1532 
1533     @Test
1534     static void smokeTest2() {
1535         // Do some zipping and shuffling.
1536         DoubleVector io = (DoubleVector) SPECIES.broadcast(0).addIndex(1);
1537         DoubleVector io2 = (DoubleVector) VectorShuffle.iota(SPECIES,0,1,false).toVector();
1538         Assert.assertEquals(io, io2);
1539         DoubleVector a = io.add((double)1); //[1,2]
1540         DoubleVector b = a.neg();  //[-1,-2]
1541         double[] abValues = bothToArray(a,b); //[1,2,-1,-2]
1542         VectorShuffle<Double> zip0 = VectorShuffle.makeZip(SPECIES, 0);
1543         VectorShuffle<Double> zip1 = VectorShuffle.makeZip(SPECIES, 1);
1544         DoubleVector zab0 = a.rearrange(zip0,b); //[1,-1]
1545         DoubleVector zab1 = a.rearrange(zip1,b); //[2,-2]
1546         double[] zabValues = bothToArray(zab0, zab1); //[1,-1,2,-2]
1547         // manually zip
1548         double[] manual = new double[zabValues.length];
1549         for (int i = 0; i < manual.length; i += 2) {
1550             manual[i+0] = abValues[i/2];
1551             manual[i+1] = abValues[a.length() + i/2];
1552         }
1553         Assert.assertEquals(Arrays.toString(zabValues), Arrays.toString(manual));
1554         VectorShuffle<Double> unz0 = VectorShuffle.makeUnzip(SPECIES, 0);
1555         VectorShuffle<Double> unz1 = VectorShuffle.makeUnzip(SPECIES, 1);
1556         DoubleVector uab0 = zab0.rearrange(unz0,zab1);
1557         DoubleVector uab1 = zab0.rearrange(unz1,zab1);
1558         double[] abValues1 = bothToArray(uab0, uab1);
1559         Assert.assertEquals(Arrays.toString(abValues), Arrays.toString(abValues1));
1560     }
1561 
1562     static void iotaShuffle() {
1563         DoubleVector io = (DoubleVector) SPECIES.broadcast(0).addIndex(1);
1564         DoubleVector io2 = (DoubleVector) VectorShuffle.iota(SPECIES, 0 , 1, false).toVector();
1565         Assert.assertEquals(io, io2);
1566     }
1567 
1568     @Test
1569     // Test all shuffle related operations.
1570     static void shuffleTest() {
1571         // To test backend instructions, make sure that C2 is used.
1572         for (int loop = 0; loop < INVOC_COUNT * INVOC_COUNT; loop++) {
1573             iotaShuffle();
1574         }
1575     }
1576 
1577     @Test
1578     void viewAsIntegeralLanesTest() {
1579         Vector<?> asIntegral = SPECIES.zero().viewAsIntegralLanes();
1580         VectorSpecies<?> asIntegralSpecies = asIntegral.species();
1581         Assert.assertNotEquals(asIntegralSpecies.elementType(), SPECIES.elementType());
1582         Assert.assertEquals(asIntegralSpecies.vectorShape(), SPECIES.vectorShape());
1583         Assert.assertEquals(asIntegralSpecies.length(), SPECIES.length());
1584         Assert.assertEquals(asIntegral.viewAsFloatingLanes().species(), SPECIES);
1585     }
1586 
1587     @Test
1588     void viewAsFloatingLanesTest() {
1589         Vector<?> asFloating = SPECIES.zero().viewAsFloatingLanes();
1590         Assert.assertEquals(asFloating.species(), SPECIES);
1591     }
1592 
1593     static double ADD(double a, double b) {
1594         return (double)(a + b);
1595     }
1596 
1597     @Test(dataProvider = "doubleBinaryOpProvider")
1598     static void ADDDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1599         double[] a = fa.apply(SPECIES.length());
1600         double[] b = fb.apply(SPECIES.length());
1601         double[] r = fr.apply(SPECIES.length());
1602 
1603         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1604             for (int i = 0; i < a.length; i += SPECIES.length()) {
1605                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1606                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1607                 av.lanewise(VectorOperators.ADD, bv).intoArray(r, i);
1608             }
1609         }
1610 
1611         assertArraysEquals(r, a, b, Double64VectorTests::ADD);
1612     }
1613 
1614     static double add(double a, double b) {
1615         return (double)(a + b);
1616     }
1617 
1618     @Test(dataProvider = "doubleBinaryOpProvider")
1619     static void addDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1620         double[] a = fa.apply(SPECIES.length());
1621         double[] b = fb.apply(SPECIES.length());
1622         double[] r = fr.apply(SPECIES.length());
1623 
1624         for (int i = 0; i < a.length; i += SPECIES.length()) {
1625             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1626             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1627             av.add(bv).intoArray(r, i);
1628         }
1629 
1630         assertArraysEquals(r, a, b, Double64VectorTests::add);
1631     }
1632 
1633     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1634     static void ADDDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
1635                                           IntFunction<boolean[]> fm) {
1636         double[] a = fa.apply(SPECIES.length());
1637         double[] b = fb.apply(SPECIES.length());
1638         double[] r = fr.apply(SPECIES.length());
1639         boolean[] mask = fm.apply(SPECIES.length());
1640         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1641 
1642         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1643             for (int i = 0; i < a.length; i += SPECIES.length()) {
1644                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1645                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1646                 av.lanewise(VectorOperators.ADD, bv, vmask).intoArray(r, i);
1647             }
1648         }
1649 
1650         assertArraysEquals(r, a, b, mask, Double64VectorTests::ADD);
1651     }
1652 
1653     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1654     static void addDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
1655                                           IntFunction<boolean[]> fm) {
1656         double[] a = fa.apply(SPECIES.length());
1657         double[] b = fb.apply(SPECIES.length());
1658         double[] r = fr.apply(SPECIES.length());
1659         boolean[] mask = fm.apply(SPECIES.length());
1660         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1661 
1662         for (int i = 0; i < a.length; i += SPECIES.length()) {
1663             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1664             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1665             av.add(bv, vmask).intoArray(r, i);
1666         }
1667 
1668         assertArraysEquals(r, a, b, mask, Double64VectorTests::add);
1669     }
1670 
1671     static double SUB(double a, double b) {
1672         return (double)(a - b);
1673     }
1674 
1675     @Test(dataProvider = "doubleBinaryOpProvider")
1676     static void SUBDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1677         double[] a = fa.apply(SPECIES.length());
1678         double[] b = fb.apply(SPECIES.length());
1679         double[] r = fr.apply(SPECIES.length());
1680 
1681         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1682             for (int i = 0; i < a.length; i += SPECIES.length()) {
1683                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1684                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1685                 av.lanewise(VectorOperators.SUB, bv).intoArray(r, i);
1686             }
1687         }
1688 
1689         assertArraysEquals(r, a, b, Double64VectorTests::SUB);
1690     }
1691 
1692     static double sub(double a, double b) {
1693         return (double)(a - b);
1694     }
1695 
1696     @Test(dataProvider = "doubleBinaryOpProvider")
1697     static void subDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1698         double[] a = fa.apply(SPECIES.length());
1699         double[] b = fb.apply(SPECIES.length());
1700         double[] r = fr.apply(SPECIES.length());
1701 
1702         for (int i = 0; i < a.length; i += SPECIES.length()) {
1703             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1704             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1705             av.sub(bv).intoArray(r, i);
1706         }
1707 
1708         assertArraysEquals(r, a, b, Double64VectorTests::sub);
1709     }
1710 
1711     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1712     static void SUBDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
1713                                           IntFunction<boolean[]> fm) {
1714         double[] a = fa.apply(SPECIES.length());
1715         double[] b = fb.apply(SPECIES.length());
1716         double[] r = fr.apply(SPECIES.length());
1717         boolean[] mask = fm.apply(SPECIES.length());
1718         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1719 
1720         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1721             for (int i = 0; i < a.length; i += SPECIES.length()) {
1722                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1723                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1724                 av.lanewise(VectorOperators.SUB, bv, vmask).intoArray(r, i);
1725             }
1726         }
1727 
1728         assertArraysEquals(r, a, b, mask, Double64VectorTests::SUB);
1729     }
1730 
1731     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1732     static void subDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
1733                                           IntFunction<boolean[]> fm) {
1734         double[] a = fa.apply(SPECIES.length());
1735         double[] b = fb.apply(SPECIES.length());
1736         double[] r = fr.apply(SPECIES.length());
1737         boolean[] mask = fm.apply(SPECIES.length());
1738         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1739 
1740         for (int i = 0; i < a.length; i += SPECIES.length()) {
1741             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1742             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1743             av.sub(bv, vmask).intoArray(r, i);
1744         }
1745 
1746         assertArraysEquals(r, a, b, mask, Double64VectorTests::sub);
1747     }
1748 
1749     static double MUL(double a, double b) {
1750         return (double)(a * b);
1751     }
1752 
1753     @Test(dataProvider = "doubleBinaryOpProvider")
1754     static void MULDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1755         double[] a = fa.apply(SPECIES.length());
1756         double[] b = fb.apply(SPECIES.length());
1757         double[] r = fr.apply(SPECIES.length());
1758 
1759         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1760             for (int i = 0; i < a.length; i += SPECIES.length()) {
1761                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1762                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1763                 av.lanewise(VectorOperators.MUL, bv).intoArray(r, i);
1764             }
1765         }
1766 
1767         assertArraysEquals(r, a, b, Double64VectorTests::MUL);
1768     }
1769 
1770     static double mul(double a, double b) {
1771         return (double)(a * b);
1772     }
1773 
1774     @Test(dataProvider = "doubleBinaryOpProvider")
1775     static void mulDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1776         double[] a = fa.apply(SPECIES.length());
1777         double[] b = fb.apply(SPECIES.length());
1778         double[] r = fr.apply(SPECIES.length());
1779 
1780         for (int i = 0; i < a.length; i += SPECIES.length()) {
1781             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1782             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1783             av.mul(bv).intoArray(r, i);
1784         }
1785 
1786         assertArraysEquals(r, a, b, Double64VectorTests::mul);
1787     }
1788 
1789     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1790     static void MULDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
1791                                           IntFunction<boolean[]> fm) {
1792         double[] a = fa.apply(SPECIES.length());
1793         double[] b = fb.apply(SPECIES.length());
1794         double[] r = fr.apply(SPECIES.length());
1795         boolean[] mask = fm.apply(SPECIES.length());
1796         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1797 
1798         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1799             for (int i = 0; i < a.length; i += SPECIES.length()) {
1800                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1801                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1802                 av.lanewise(VectorOperators.MUL, bv, vmask).intoArray(r, i);
1803             }
1804         }
1805 
1806         assertArraysEquals(r, a, b, mask, Double64VectorTests::MUL);
1807     }
1808 
1809     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1810     static void mulDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
1811                                           IntFunction<boolean[]> fm) {
1812         double[] a = fa.apply(SPECIES.length());
1813         double[] b = fb.apply(SPECIES.length());
1814         double[] r = fr.apply(SPECIES.length());
1815         boolean[] mask = fm.apply(SPECIES.length());
1816         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1817 
1818         for (int i = 0; i < a.length; i += SPECIES.length()) {
1819             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1820             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1821             av.mul(bv, vmask).intoArray(r, i);
1822         }
1823 
1824         assertArraysEquals(r, a, b, mask, Double64VectorTests::mul);
1825     }
1826 
1827     static double DIV(double a, double b) {
1828         return (double)(a / b);
1829     }
1830 
1831     @Test(dataProvider = "doubleBinaryOpProvider")
1832     static void DIVDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1833         double[] a = fa.apply(SPECIES.length());
1834         double[] b = fb.apply(SPECIES.length());
1835         double[] r = fr.apply(SPECIES.length());
1836 
1837         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1838             for (int i = 0; i < a.length; i += SPECIES.length()) {
1839                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1840                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1841                 av.lanewise(VectorOperators.DIV, bv).intoArray(r, i);
1842             }
1843         }
1844 
1845         assertArraysEquals(r, a, b, Double64VectorTests::DIV);
1846     }
1847 
1848     static double div(double a, double b) {
1849         return (double)(a / b);
1850     }
1851 
1852     @Test(dataProvider = "doubleBinaryOpProvider")
1853     static void divDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1854         double[] a = fa.apply(SPECIES.length());
1855         double[] b = fb.apply(SPECIES.length());
1856         double[] r = fr.apply(SPECIES.length());
1857 
1858         for (int i = 0; i < a.length; i += SPECIES.length()) {
1859             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1860             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1861             av.div(bv).intoArray(r, i);
1862         }
1863 
1864         assertArraysEquals(r, a, b, Double64VectorTests::div);
1865     }
1866 
1867     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1868     static void DIVDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
1869                                           IntFunction<boolean[]> fm) {
1870         double[] a = fa.apply(SPECIES.length());
1871         double[] b = fb.apply(SPECIES.length());
1872         double[] r = fr.apply(SPECIES.length());
1873         boolean[] mask = fm.apply(SPECIES.length());
1874         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1875 
1876         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1877             for (int i = 0; i < a.length; i += SPECIES.length()) {
1878                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1879                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1880                 av.lanewise(VectorOperators.DIV, bv, vmask).intoArray(r, i);
1881             }
1882         }
1883 
1884         assertArraysEquals(r, a, b, mask, Double64VectorTests::DIV);
1885     }
1886 
1887     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1888     static void divDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
1889                                           IntFunction<boolean[]> fm) {
1890         double[] a = fa.apply(SPECIES.length());
1891         double[] b = fb.apply(SPECIES.length());
1892         double[] r = fr.apply(SPECIES.length());
1893         boolean[] mask = fm.apply(SPECIES.length());
1894         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1895 
1896         for (int i = 0; i < a.length; i += SPECIES.length()) {
1897             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1898             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1899             av.div(bv, vmask).intoArray(r, i);
1900         }
1901 
1902         assertArraysEquals(r, a, b, mask, Double64VectorTests::div);
1903     }
1904 
1905     static double FIRST_NONZERO(double a, double b) {
1906         return (double)(Double.doubleToLongBits(a)!=0?a:b);
1907     }
1908 
1909     @Test(dataProvider = "doubleBinaryOpProvider")
1910     static void FIRST_NONZERODouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1911         double[] a = fa.apply(SPECIES.length());
1912         double[] b = fb.apply(SPECIES.length());
1913         double[] r = fr.apply(SPECIES.length());
1914 
1915         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1916             for (int i = 0; i < a.length; i += SPECIES.length()) {
1917                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1918                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1919                 av.lanewise(VectorOperators.FIRST_NONZERO, bv).intoArray(r, i);
1920             }
1921         }
1922 
1923         assertArraysEquals(r, a, b, Double64VectorTests::FIRST_NONZERO);
1924     }
1925 
1926     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1927     static void FIRST_NONZERODouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
1928                                           IntFunction<boolean[]> fm) {
1929         double[] a = fa.apply(SPECIES.length());
1930         double[] b = fb.apply(SPECIES.length());
1931         double[] r = fr.apply(SPECIES.length());
1932         boolean[] mask = fm.apply(SPECIES.length());
1933         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1934 
1935         for (int ic = 0; ic < INVOC_COUNT; ic++) {
1936             for (int i = 0; i < a.length; i += SPECIES.length()) {
1937                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1938                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
1939                 av.lanewise(VectorOperators.FIRST_NONZERO, bv, vmask).intoArray(r, i);
1940             }
1941         }
1942 
1943         assertArraysEquals(r, a, b, mask, Double64VectorTests::FIRST_NONZERO);
1944     }
1945 
1946     @Test(dataProvider = "doubleBinaryOpProvider")
1947     static void addDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1948         double[] a = fa.apply(SPECIES.length());
1949         double[] b = fb.apply(SPECIES.length());
1950         double[] r = fr.apply(SPECIES.length());
1951 
1952         for (int i = 0; i < a.length; i += SPECIES.length()) {
1953             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1954             av.add(b[i]).intoArray(r, i);
1955         }
1956 
1957         assertBroadcastArraysEquals(r, a, b, Double64VectorTests::add);
1958     }
1959 
1960     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1961     static void addDouble64VectorTestsBroadcastMaskedSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb,
1962                                           IntFunction<boolean[]> fm) {
1963         double[] a = fa.apply(SPECIES.length());
1964         double[] b = fb.apply(SPECIES.length());
1965         double[] r = fr.apply(SPECIES.length());
1966         boolean[] mask = fm.apply(SPECIES.length());
1967         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1968 
1969         for (int i = 0; i < a.length; i += SPECIES.length()) {
1970             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1971             av.add(b[i], vmask).intoArray(r, i);
1972         }
1973 
1974         assertBroadcastArraysEquals(r, a, b, mask, Double64VectorTests::add);
1975     }
1976 
1977     @Test(dataProvider = "doubleBinaryOpProvider")
1978     static void subDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
1979         double[] a = fa.apply(SPECIES.length());
1980         double[] b = fb.apply(SPECIES.length());
1981         double[] r = fr.apply(SPECIES.length());
1982 
1983         for (int i = 0; i < a.length; i += SPECIES.length()) {
1984             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
1985             av.sub(b[i]).intoArray(r, i);
1986         }
1987 
1988         assertBroadcastArraysEquals(r, a, b, Double64VectorTests::sub);
1989     }
1990 
1991     @Test(dataProvider = "doubleBinaryOpMaskProvider")
1992     static void subDouble64VectorTestsBroadcastMaskedSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb,
1993                                           IntFunction<boolean[]> fm) {
1994         double[] a = fa.apply(SPECIES.length());
1995         double[] b = fb.apply(SPECIES.length());
1996         double[] r = fr.apply(SPECIES.length());
1997         boolean[] mask = fm.apply(SPECIES.length());
1998         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
1999 
2000         for (int i = 0; i < a.length; i += SPECIES.length()) {
2001             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2002             av.sub(b[i], vmask).intoArray(r, i);
2003         }
2004 
2005         assertBroadcastArraysEquals(r, a, b, mask, Double64VectorTests::sub);
2006     }
2007 
2008     @Test(dataProvider = "doubleBinaryOpProvider")
2009     static void mulDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2010         double[] a = fa.apply(SPECIES.length());
2011         double[] b = fb.apply(SPECIES.length());
2012         double[] r = fr.apply(SPECIES.length());
2013 
2014         for (int i = 0; i < a.length; i += SPECIES.length()) {
2015             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2016             av.mul(b[i]).intoArray(r, i);
2017         }
2018 
2019         assertBroadcastArraysEquals(r, a, b, Double64VectorTests::mul);
2020     }
2021 
2022     @Test(dataProvider = "doubleBinaryOpMaskProvider")
2023     static void mulDouble64VectorTestsBroadcastMaskedSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb,
2024                                           IntFunction<boolean[]> fm) {
2025         double[] a = fa.apply(SPECIES.length());
2026         double[] b = fb.apply(SPECIES.length());
2027         double[] r = fr.apply(SPECIES.length());
2028         boolean[] mask = fm.apply(SPECIES.length());
2029         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2030 
2031         for (int i = 0; i < a.length; i += SPECIES.length()) {
2032             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2033             av.mul(b[i], vmask).intoArray(r, i);
2034         }
2035 
2036         assertBroadcastArraysEquals(r, a, b, mask, Double64VectorTests::mul);
2037     }
2038 
2039     @Test(dataProvider = "doubleBinaryOpProvider")
2040     static void divDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2041         double[] a = fa.apply(SPECIES.length());
2042         double[] b = fb.apply(SPECIES.length());
2043         double[] r = fr.apply(SPECIES.length());
2044 
2045         for (int i = 0; i < a.length; i += SPECIES.length()) {
2046             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2047             av.div(b[i]).intoArray(r, i);
2048         }
2049 
2050         assertBroadcastArraysEquals(r, a, b, Double64VectorTests::div);
2051     }
2052 
2053     @Test(dataProvider = "doubleBinaryOpMaskProvider")
2054     static void divDouble64VectorTestsBroadcastMaskedSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb,
2055                                           IntFunction<boolean[]> fm) {
2056         double[] a = fa.apply(SPECIES.length());
2057         double[] b = fb.apply(SPECIES.length());
2058         double[] r = fr.apply(SPECIES.length());
2059         boolean[] mask = fm.apply(SPECIES.length());
2060         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2061 
2062         for (int i = 0; i < a.length; i += SPECIES.length()) {
2063             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2064             av.div(b[i], vmask).intoArray(r, i);
2065         }
2066 
2067         assertBroadcastArraysEquals(r, a, b, mask, Double64VectorTests::div);
2068     }
2069 
2070     @Test(dataProvider = "doubleBinaryOpProvider")
2071     static void ADDDouble64VectorTestsBroadcastLongSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2072         double[] a = fa.apply(SPECIES.length());
2073         double[] b = fb.apply(SPECIES.length());
2074         double[] r = fr.apply(SPECIES.length());
2075 
2076         for (int i = 0; i < a.length; i += SPECIES.length()) {
2077             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2078             av.lanewise(VectorOperators.ADD, (long)b[i]).intoArray(r, i);
2079         }
2080 
2081         assertBroadcastLongArraysEquals(r, a, b, Double64VectorTests::ADD);
2082     }
2083 
2084     @Test(dataProvider = "doubleBinaryOpMaskProvider")
2085     static void ADDDouble64VectorTestsBroadcastMaskedLongSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb,
2086                                           IntFunction<boolean[]> fm) {
2087         double[] a = fa.apply(SPECIES.length());
2088         double[] b = fb.apply(SPECIES.length());
2089         double[] r = fr.apply(SPECIES.length());
2090         boolean[] mask = fm.apply(SPECIES.length());
2091         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2092 
2093         for (int i = 0; i < a.length; i += SPECIES.length()) {
2094             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2095             av.lanewise(VectorOperators.ADD, (long)b[i], vmask).intoArray(r, i);
2096         }
2097 
2098         assertBroadcastLongArraysEquals(r, a, b, mask, Double64VectorTests::ADD);
2099     }
2100 
2101     @Test(dataProvider = "doubleUnaryOpProvider")
2102     static void MINDouble64VectorTestsWithMemOp(IntFunction<double[]> fa) {
2103         double[] a = fa.apply(SPECIES.length());
2104         double[] r = fr.apply(SPECIES.length());
2105 
2106         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2107             for (int i = 0; i < a.length; i += SPECIES.length()) {
2108                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2109                 av.lanewise(VectorOperators.MIN, bcast_vec).intoArray(r, i);
2110             }
2111         }
2112 
2113         assertArraysEquals(r, a, (double)10, Double64VectorTests::MIN);
2114     }
2115 
2116     @Test(dataProvider = "doubleUnaryOpProvider")
2117     static void minDouble64VectorTestsWithMemOp(IntFunction<double[]> fa) {
2118         double[] a = fa.apply(SPECIES.length());
2119         double[] r = fr.apply(SPECIES.length());
2120 
2121         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2122             for (int i = 0; i < a.length; i += SPECIES.length()) {
2123                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2124                 av.min(bcast_vec).intoArray(r, i);
2125             }
2126         }
2127 
2128         assertArraysEquals(r, a, (double)10, Double64VectorTests::min);
2129     }
2130 
2131     @Test(dataProvider = "doubleUnaryOpMaskProvider")
2132     static void MINDouble64VectorTestsMaskedWithMemOp(IntFunction<double[]> fa, IntFunction<boolean[]> fm) {
2133         double[] a = fa.apply(SPECIES.length());
2134         double[] r = fr.apply(SPECIES.length());
2135         boolean[] mask = fm.apply(SPECIES.length());
2136         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2137 
2138         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2139             for (int i = 0; i < a.length; i += SPECIES.length()) {
2140                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2141                 av.lanewise(VectorOperators.MIN, bcast_vec, vmask).intoArray(r, i);
2142             }
2143         }
2144 
2145         assertArraysEquals(r, a, (double)10, mask, Double64VectorTests::MIN);
2146     }
2147 
2148     @Test(dataProvider = "doubleUnaryOpProvider")
2149     static void MAXDouble64VectorTestsWithMemOp(IntFunction<double[]> fa) {
2150         double[] a = fa.apply(SPECIES.length());
2151         double[] r = fr.apply(SPECIES.length());
2152 
2153         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2154             for (int i = 0; i < a.length; i += SPECIES.length()) {
2155                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2156                 av.lanewise(VectorOperators.MAX, bcast_vec).intoArray(r, i);
2157             }
2158         }
2159 
2160         assertArraysEquals(r, a, (double)10, Double64VectorTests::MAX);
2161     }
2162 
2163     @Test(dataProvider = "doubleUnaryOpProvider")
2164     static void maxDouble64VectorTestsWithMemOp(IntFunction<double[]> fa) {
2165         double[] a = fa.apply(SPECIES.length());
2166         double[] r = fr.apply(SPECIES.length());
2167 
2168         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2169             for (int i = 0; i < a.length; i += SPECIES.length()) {
2170                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2171                 av.max(bcast_vec).intoArray(r, i);
2172             }
2173         }
2174 
2175         assertArraysEquals(r, a, (double)10, Double64VectorTests::max);
2176     }
2177 
2178     @Test(dataProvider = "doubleUnaryOpMaskProvider")
2179     static void MAXDouble64VectorTestsMaskedWithMemOp(IntFunction<double[]> fa, IntFunction<boolean[]> fm) {
2180         double[] a = fa.apply(SPECIES.length());
2181         double[] r = fr.apply(SPECIES.length());
2182         boolean[] mask = fm.apply(SPECIES.length());
2183         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2184 
2185         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2186             for (int i = 0; i < a.length; i += SPECIES.length()) {
2187                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2188                 av.lanewise(VectorOperators.MAX, bcast_vec, vmask).intoArray(r, i);
2189             }
2190         }
2191 
2192         assertArraysEquals(r, a, (double)10, mask, Double64VectorTests::MAX);
2193     }
2194 
2195     static double MIN(double a, double b) {
2196         return (double)(Math.min(a, b));
2197     }
2198 
2199     @Test(dataProvider = "doubleBinaryOpProvider")
2200     static void MINDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2201         double[] a = fa.apply(SPECIES.length());
2202         double[] b = fb.apply(SPECIES.length());
2203         double[] r = fr.apply(SPECIES.length());
2204 
2205         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2206             for (int i = 0; i < a.length; i += SPECIES.length()) {
2207                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2208                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
2209                 av.lanewise(VectorOperators.MIN, bv).intoArray(r, i);
2210             }
2211         }
2212 
2213         assertArraysEquals(r, a, b, Double64VectorTests::MIN);
2214     }
2215 
2216     static double min(double a, double b) {
2217         return (double)(Math.min(a, b));
2218     }
2219 
2220     @Test(dataProvider = "doubleBinaryOpProvider")
2221     static void minDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2222         double[] a = fa.apply(SPECIES.length());
2223         double[] b = fb.apply(SPECIES.length());
2224         double[] r = fr.apply(SPECIES.length());
2225 
2226         for (int i = 0; i < a.length; i += SPECIES.length()) {
2227             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2228             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
2229             av.min(bv).intoArray(r, i);
2230         }
2231 
2232         assertArraysEquals(r, a, b, Double64VectorTests::min);
2233     }
2234 
2235     static double MAX(double a, double b) {
2236         return (double)(Math.max(a, b));
2237     }
2238 
2239     @Test(dataProvider = "doubleBinaryOpProvider")
2240     static void MAXDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2241         double[] a = fa.apply(SPECIES.length());
2242         double[] b = fb.apply(SPECIES.length());
2243         double[] r = fr.apply(SPECIES.length());
2244 
2245         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2246             for (int i = 0; i < a.length; i += SPECIES.length()) {
2247                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2248                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
2249                 av.lanewise(VectorOperators.MAX, bv).intoArray(r, i);
2250             }
2251         }
2252 
2253         assertArraysEquals(r, a, b, Double64VectorTests::MAX);
2254     }
2255 
2256     static double max(double a, double b) {
2257         return (double)(Math.max(a, b));
2258     }
2259 
2260     @Test(dataProvider = "doubleBinaryOpProvider")
2261     static void maxDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2262         double[] a = fa.apply(SPECIES.length());
2263         double[] b = fb.apply(SPECIES.length());
2264         double[] r = fr.apply(SPECIES.length());
2265 
2266         for (int i = 0; i < a.length; i += SPECIES.length()) {
2267             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2268             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
2269             av.max(bv).intoArray(r, i);
2270         }
2271 
2272         assertArraysEquals(r, a, b, Double64VectorTests::max);
2273     }
2274 
2275     @Test(dataProvider = "doubleBinaryOpProvider")
2276     static void MINDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2277         double[] a = fa.apply(SPECIES.length());
2278         double[] b = fb.apply(SPECIES.length());
2279         double[] r = fr.apply(SPECIES.length());
2280 
2281         for (int i = 0; i < a.length; i += SPECIES.length()) {
2282             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2283             av.lanewise(VectorOperators.MIN, b[i]).intoArray(r, i);
2284         }
2285 
2286         assertBroadcastArraysEquals(r, a, b, Double64VectorTests::MIN);
2287     }
2288 
2289     @Test(dataProvider = "doubleBinaryOpProvider")
2290     static void minDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2291         double[] a = fa.apply(SPECIES.length());
2292         double[] b = fb.apply(SPECIES.length());
2293         double[] r = fr.apply(SPECIES.length());
2294 
2295         for (int i = 0; i < a.length; i += SPECIES.length()) {
2296             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2297             av.min(b[i]).intoArray(r, i);
2298         }
2299 
2300         assertBroadcastArraysEquals(r, a, b, Double64VectorTests::min);
2301     }
2302 
2303     @Test(dataProvider = "doubleBinaryOpProvider")
2304     static void MAXDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2305         double[] a = fa.apply(SPECIES.length());
2306         double[] b = fb.apply(SPECIES.length());
2307         double[] r = fr.apply(SPECIES.length());
2308 
2309         for (int i = 0; i < a.length; i += SPECIES.length()) {
2310             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2311             av.lanewise(VectorOperators.MAX, b[i]).intoArray(r, i);
2312         }
2313 
2314         assertBroadcastArraysEquals(r, a, b, Double64VectorTests::MAX);
2315     }
2316 
2317     @Test(dataProvider = "doubleBinaryOpProvider")
2318     static void maxDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
2319         double[] a = fa.apply(SPECIES.length());
2320         double[] b = fb.apply(SPECIES.length());
2321         double[] r = fr.apply(SPECIES.length());
2322 
2323         for (int i = 0; i < a.length; i += SPECIES.length()) {
2324             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2325             av.max(b[i]).intoArray(r, i);
2326         }
2327 
2328         assertBroadcastArraysEquals(r, a, b, Double64VectorTests::max);
2329     }
2330 
2331     static double ADDReduce(double[] a, int idx) {
2332         double res = 0;
2333         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2334             res += a[i];
2335         }
2336 
2337         return res;
2338     }
2339 
2340     static double ADDReduceAll(double[] a) {
2341         double res = 0;
2342         for (int i = 0; i < a.length; i += SPECIES.length()) {
2343             res += ADDReduce(a, i);
2344         }
2345 
2346         return res;
2347     }
2348 
2349     @Test(dataProvider = "doubleUnaryOpProvider")
2350     static void ADDReduceDouble64VectorTests(IntFunction<double[]> fa) {
2351         double[] a = fa.apply(SPECIES.length());
2352         double[] r = fr.apply(SPECIES.length());
2353         double ra = 0;
2354 
2355         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2356             for (int i = 0; i < a.length; i += SPECIES.length()) {
2357                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2358                 r[i] = av.reduceLanes(VectorOperators.ADD);
2359             }
2360         }
2361 
2362         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2363             ra = 0;
2364             for (int i = 0; i < a.length; i += SPECIES.length()) {
2365                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2366                 ra += av.reduceLanes(VectorOperators.ADD);
2367             }
2368         }
2369 
2370         assertReductionArraysEquals(r, ra, a,
2371                 Double64VectorTests::ADDReduce, Double64VectorTests::ADDReduceAll, RELATIVE_ROUNDING_ERROR_FACTOR_ADD);
2372     }
2373 
2374     static double ADDReduceMasked(double[] a, int idx, boolean[] mask) {
2375         double res = 0;
2376         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2377             if (mask[i % SPECIES.length()])
2378                 res += a[i];
2379         }
2380 
2381         return res;
2382     }
2383 
2384     static double ADDReduceAllMasked(double[] a, boolean[] mask) {
2385         double res = 0;
2386         for (int i = 0; i < a.length; i += SPECIES.length()) {
2387             res += ADDReduceMasked(a, i, mask);
2388         }
2389 
2390         return res;
2391     }
2392 
2393     @Test(dataProvider = "doubleUnaryOpMaskProvider")
2394     static void ADDReduceDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<boolean[]> fm) {
2395         double[] a = fa.apply(SPECIES.length());
2396         double[] r = fr.apply(SPECIES.length());
2397         boolean[] mask = fm.apply(SPECIES.length());
2398         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2399         double ra = 0;
2400 
2401         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2402             for (int i = 0; i < a.length; i += SPECIES.length()) {
2403                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2404                 r[i] = av.reduceLanes(VectorOperators.ADD, vmask);
2405             }
2406         }
2407 
2408         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2409             ra = 0;
2410             for (int i = 0; i < a.length; i += SPECIES.length()) {
2411                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2412                 ra += av.reduceLanes(VectorOperators.ADD, vmask);
2413             }
2414         }
2415 
2416         assertReductionArraysEqualsMasked(r, ra, a, mask,
2417                 Double64VectorTests::ADDReduceMasked, Double64VectorTests::ADDReduceAllMasked, RELATIVE_ROUNDING_ERROR_FACTOR_ADD);
2418     }
2419 
2420     static double MULReduce(double[] a, int idx) {
2421         double res = 1;
2422         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2423             res *= a[i];
2424         }
2425 
2426         return res;
2427     }
2428 
2429     static double MULReduceAll(double[] a) {
2430         double res = 1;
2431         for (int i = 0; i < a.length; i += SPECIES.length()) {
2432             res *= MULReduce(a, i);
2433         }
2434 
2435         return res;
2436     }
2437 
2438     @Test(dataProvider = "doubleUnaryOpProvider")
2439     static void MULReduceDouble64VectorTests(IntFunction<double[]> fa) {
2440         double[] a = fa.apply(SPECIES.length());
2441         double[] r = fr.apply(SPECIES.length());
2442         double ra = 1;
2443 
2444         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2445             for (int i = 0; i < a.length; i += SPECIES.length()) {
2446                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2447                 r[i] = av.reduceLanes(VectorOperators.MUL);
2448             }
2449         }
2450 
2451         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2452             ra = 1;
2453             for (int i = 0; i < a.length; i += SPECIES.length()) {
2454                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2455                 ra *= av.reduceLanes(VectorOperators.MUL);
2456             }
2457         }
2458 
2459         assertReductionArraysEquals(r, ra, a,
2460                 Double64VectorTests::MULReduce, Double64VectorTests::MULReduceAll, RELATIVE_ROUNDING_ERROR_FACTOR_MUL);
2461     }
2462 
2463     static double MULReduceMasked(double[] a, int idx, boolean[] mask) {
2464         double res = 1;
2465         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2466             if (mask[i % SPECIES.length()])
2467                 res *= a[i];
2468         }
2469 
2470         return res;
2471     }
2472 
2473     static double MULReduceAllMasked(double[] a, boolean[] mask) {
2474         double res = 1;
2475         for (int i = 0; i < a.length; i += SPECIES.length()) {
2476             res *= MULReduceMasked(a, i, mask);
2477         }
2478 
2479         return res;
2480     }
2481 
2482     @Test(dataProvider = "doubleUnaryOpMaskProvider")
2483     static void MULReduceDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<boolean[]> fm) {
2484         double[] a = fa.apply(SPECIES.length());
2485         double[] r = fr.apply(SPECIES.length());
2486         boolean[] mask = fm.apply(SPECIES.length());
2487         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2488         double ra = 1;
2489 
2490         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2491             for (int i = 0; i < a.length; i += SPECIES.length()) {
2492                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2493                 r[i] = av.reduceLanes(VectorOperators.MUL, vmask);
2494             }
2495         }
2496 
2497         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2498             ra = 1;
2499             for (int i = 0; i < a.length; i += SPECIES.length()) {
2500                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2501                 ra *= av.reduceLanes(VectorOperators.MUL, vmask);
2502             }
2503         }
2504 
2505         assertReductionArraysEqualsMasked(r, ra, a, mask,
2506                 Double64VectorTests::MULReduceMasked, Double64VectorTests::MULReduceAllMasked, RELATIVE_ROUNDING_ERROR_FACTOR_MUL);
2507     }
2508 
2509     static double MINReduce(double[] a, int idx) {
2510         double res = Double.POSITIVE_INFINITY;
2511         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2512             res = (double) Math.min(res, a[i]);
2513         }
2514 
2515         return res;
2516     }
2517 
2518     static double MINReduceAll(double[] a) {
2519         double res = Double.POSITIVE_INFINITY;
2520         for (int i = 0; i < a.length; i += SPECIES.length()) {
2521             res = (double) Math.min(res, MINReduce(a, i));
2522         }
2523 
2524         return res;
2525     }
2526 
2527     @Test(dataProvider = "doubleUnaryOpProvider")
2528     static void MINReduceDouble64VectorTests(IntFunction<double[]> fa) {
2529         double[] a = fa.apply(SPECIES.length());
2530         double[] r = fr.apply(SPECIES.length());
2531         double ra = Double.POSITIVE_INFINITY;
2532 
2533         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2534             for (int i = 0; i < a.length; i += SPECIES.length()) {
2535                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2536                 r[i] = av.reduceLanes(VectorOperators.MIN);
2537             }
2538         }
2539 
2540         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2541             ra = Double.POSITIVE_INFINITY;
2542             for (int i = 0; i < a.length; i += SPECIES.length()) {
2543                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2544                 ra = (double) Math.min(ra, av.reduceLanes(VectorOperators.MIN));
2545             }
2546         }
2547 
2548         assertReductionArraysEquals(r, ra, a,
2549                 Double64VectorTests::MINReduce, Double64VectorTests::MINReduceAll);
2550     }
2551 
2552     static double MINReduceMasked(double[] a, int idx, boolean[] mask) {
2553         double res = Double.POSITIVE_INFINITY;
2554         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2555             if (mask[i % SPECIES.length()])
2556                 res = (double) Math.min(res, a[i]);
2557         }
2558 
2559         return res;
2560     }
2561 
2562     static double MINReduceAllMasked(double[] a, boolean[] mask) {
2563         double res = Double.POSITIVE_INFINITY;
2564         for (int i = 0; i < a.length; i += SPECIES.length()) {
2565             res = (double) Math.min(res, MINReduceMasked(a, i, mask));
2566         }
2567 
2568         return res;
2569     }
2570 
2571     @Test(dataProvider = "doubleUnaryOpMaskProvider")
2572     static void MINReduceDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<boolean[]> fm) {
2573         double[] a = fa.apply(SPECIES.length());
2574         double[] r = fr.apply(SPECIES.length());
2575         boolean[] mask = fm.apply(SPECIES.length());
2576         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2577         double ra = Double.POSITIVE_INFINITY;
2578 
2579         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2580             for (int i = 0; i < a.length; i += SPECIES.length()) {
2581                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2582                 r[i] = av.reduceLanes(VectorOperators.MIN, vmask);
2583             }
2584         }
2585 
2586         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2587             ra = Double.POSITIVE_INFINITY;
2588             for (int i = 0; i < a.length; i += SPECIES.length()) {
2589                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2590                 ra = (double) Math.min(ra, av.reduceLanes(VectorOperators.MIN, vmask));
2591             }
2592         }
2593 
2594         assertReductionArraysEqualsMasked(r, ra, a, mask,
2595                 Double64VectorTests::MINReduceMasked, Double64VectorTests::MINReduceAllMasked);
2596     }
2597 
2598     static double MAXReduce(double[] a, int idx) {
2599         double res = Double.NEGATIVE_INFINITY;
2600         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2601             res = (double) Math.max(res, a[i]);
2602         }
2603 
2604         return res;
2605     }
2606 
2607     static double MAXReduceAll(double[] a) {
2608         double res = Double.NEGATIVE_INFINITY;
2609         for (int i = 0; i < a.length; i += SPECIES.length()) {
2610             res = (double) Math.max(res, MAXReduce(a, i));
2611         }
2612 
2613         return res;
2614     }
2615 
2616     @Test(dataProvider = "doubleUnaryOpProvider")
2617     static void MAXReduceDouble64VectorTests(IntFunction<double[]> fa) {
2618         double[] a = fa.apply(SPECIES.length());
2619         double[] r = fr.apply(SPECIES.length());
2620         double ra = Double.NEGATIVE_INFINITY;
2621 
2622         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2623             for (int i = 0; i < a.length; i += SPECIES.length()) {
2624                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2625                 r[i] = av.reduceLanes(VectorOperators.MAX);
2626             }
2627         }
2628 
2629         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2630             ra = Double.NEGATIVE_INFINITY;
2631             for (int i = 0; i < a.length; i += SPECIES.length()) {
2632                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2633                 ra = (double) Math.max(ra, av.reduceLanes(VectorOperators.MAX));
2634             }
2635         }
2636 
2637         assertReductionArraysEquals(r, ra, a,
2638                 Double64VectorTests::MAXReduce, Double64VectorTests::MAXReduceAll);
2639     }
2640 
2641     static double MAXReduceMasked(double[] a, int idx, boolean[] mask) {
2642         double res = Double.NEGATIVE_INFINITY;
2643         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2644             if (mask[i % SPECIES.length()])
2645                 res = (double) Math.max(res, a[i]);
2646         }
2647 
2648         return res;
2649     }
2650 
2651     static double MAXReduceAllMasked(double[] a, boolean[] mask) {
2652         double res = Double.NEGATIVE_INFINITY;
2653         for (int i = 0; i < a.length; i += SPECIES.length()) {
2654             res = (double) Math.max(res, MAXReduceMasked(a, i, mask));
2655         }
2656 
2657         return res;
2658     }
2659 
2660     @Test(dataProvider = "doubleUnaryOpMaskProvider")
2661     static void MAXReduceDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<boolean[]> fm) {
2662         double[] a = fa.apply(SPECIES.length());
2663         double[] r = fr.apply(SPECIES.length());
2664         boolean[] mask = fm.apply(SPECIES.length());
2665         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2666         double ra = Double.NEGATIVE_INFINITY;
2667 
2668         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2669             for (int i = 0; i < a.length; i += SPECIES.length()) {
2670                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2671                 r[i] = av.reduceLanes(VectorOperators.MAX, vmask);
2672             }
2673         }
2674 
2675         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2676             ra = Double.NEGATIVE_INFINITY;
2677             for (int i = 0; i < a.length; i += SPECIES.length()) {
2678                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2679                 ra = (double) Math.max(ra, av.reduceLanes(VectorOperators.MAX, vmask));
2680             }
2681         }
2682 
2683         assertReductionArraysEqualsMasked(r, ra, a, mask,
2684                 Double64VectorTests::MAXReduceMasked, Double64VectorTests::MAXReduceAllMasked);
2685     }
2686 
2687     static double FIRST_NONZEROReduce(double[] a, int idx) {
2688         double res = (double) 0;
2689         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2690             res = firstNonZero(res, a[i]);
2691         }
2692 
2693         return res;
2694     }
2695 
2696     static double FIRST_NONZEROReduceAll(double[] a) {
2697         double res = (double) 0;
2698         for (int i = 0; i < a.length; i += SPECIES.length()) {
2699             res = firstNonZero(res, FIRST_NONZEROReduce(a, i));
2700         }
2701 
2702         return res;
2703     }
2704 
2705     @Test(dataProvider = "doubleUnaryOpProvider")
2706     static void FIRST_NONZEROReduceDouble64VectorTests(IntFunction<double[]> fa) {
2707         double[] a = fa.apply(SPECIES.length());
2708         double[] r = fr.apply(SPECIES.length());
2709         double ra = (double) 0;
2710 
2711         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2712             for (int i = 0; i < a.length; i += SPECIES.length()) {
2713                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2714                 r[i] = av.reduceLanes(VectorOperators.FIRST_NONZERO);
2715             }
2716         }
2717 
2718         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2719             ra = (double) 0;
2720             for (int i = 0; i < a.length; i += SPECIES.length()) {
2721                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2722                 ra = firstNonZero(ra, av.reduceLanes(VectorOperators.FIRST_NONZERO));
2723             }
2724         }
2725 
2726         assertReductionArraysEquals(r, ra, a,
2727                 Double64VectorTests::FIRST_NONZEROReduce, Double64VectorTests::FIRST_NONZEROReduceAll);
2728     }
2729 
2730     static double FIRST_NONZEROReduceMasked(double[] a, int idx, boolean[] mask) {
2731         double res = (double) 0;
2732         for (int i = idx; i < (idx + SPECIES.length()); i++) {
2733             if (mask[i % SPECIES.length()])
2734                 res = firstNonZero(res, a[i]);
2735         }
2736 
2737         return res;
2738     }
2739 
2740     static double FIRST_NONZEROReduceAllMasked(double[] a, boolean[] mask) {
2741         double res = (double) 0;
2742         for (int i = 0; i < a.length; i += SPECIES.length()) {
2743             res = firstNonZero(res, FIRST_NONZEROReduceMasked(a, i, mask));
2744         }
2745 
2746         return res;
2747     }
2748 
2749     @Test(dataProvider = "doubleUnaryOpMaskProvider")
2750     static void FIRST_NONZEROReduceDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<boolean[]> fm) {
2751         double[] a = fa.apply(SPECIES.length());
2752         double[] r = fr.apply(SPECIES.length());
2753         boolean[] mask = fm.apply(SPECIES.length());
2754         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2755         double ra = (double) 0;
2756 
2757         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2758             for (int i = 0; i < a.length; i += SPECIES.length()) {
2759                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2760                 r[i] = av.reduceLanes(VectorOperators.FIRST_NONZERO, vmask);
2761             }
2762         }
2763 
2764         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2765             ra = (double) 0;
2766             for (int i = 0; i < a.length; i += SPECIES.length()) {
2767                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2768                 ra = firstNonZero(ra, av.reduceLanes(VectorOperators.FIRST_NONZERO, vmask));
2769             }
2770         }
2771 
2772         assertReductionArraysEqualsMasked(r, ra, a, mask,
2773                 Double64VectorTests::FIRST_NONZEROReduceMasked, Double64VectorTests::FIRST_NONZEROReduceAllMasked);
2774     }
2775 
2776     @Test(dataProvider = "doubleBinaryOpProvider")
2777     static void withDouble64VectorTests(IntFunction<double []> fa, IntFunction<double []> fb) {
2778         double[] a = fa.apply(SPECIES.length());
2779         double[] b = fb.apply(SPECIES.length());
2780         double[] r = fr.apply(SPECIES.length());
2781 
2782         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2783             for (int i = 0, j = 0; i < a.length; i += SPECIES.length()) {
2784                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2785                 av.withLane(j, b[i + j]).intoArray(r, i);
2786                 a[i + j] = b[i + j];
2787                 j = (j + 1) & (SPECIES.length() - 1);
2788             }
2789         }
2790 
2791 
2792         assertArraysStrictlyEquals(r, a);
2793     }
2794 
2795     static boolean testIS_DEFAULT(double a) {
2796         return bits(a)==0;
2797     }
2798 
2799     @Test(dataProvider = "doubleTestOpProvider")
2800     static void IS_DEFAULTDouble64VectorTests(IntFunction<double[]> fa) {
2801         double[] a = fa.apply(SPECIES.length());
2802 
2803         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2804             for (int i = 0; i < a.length; i += SPECIES.length()) {
2805                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2806                 VectorMask<Double> mv = av.test(VectorOperators.IS_DEFAULT);
2807 
2808                 // Check results as part of computation.
2809                 for (int j = 0; j < SPECIES.length(); j++) {
2810                     Assert.assertEquals(mv.laneIsSet(j), testIS_DEFAULT(a[i + j]));
2811                 }
2812             }
2813         }
2814     }
2815 
2816     @Test(dataProvider = "doubleTestOpMaskProvider")
2817     static void IS_DEFAULTMaskedDouble64VectorTests(IntFunction<double[]> fa,
2818                                           IntFunction<boolean[]> fm) {
2819         double[] a = fa.apply(SPECIES.length());
2820         boolean[] mask = fm.apply(SPECIES.length());
2821         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2822 
2823         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2824             for (int i = 0; i < a.length; i += SPECIES.length()) {
2825                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2826                 VectorMask<Double> mv = av.test(VectorOperators.IS_DEFAULT, vmask);
2827 
2828                 // Check results as part of computation.
2829                 for (int j = 0; j < SPECIES.length(); j++) {
2830                     Assert.assertEquals(mv.laneIsSet(j),  vmask.laneIsSet(j) && testIS_DEFAULT(a[i + j]));
2831                 }
2832             }
2833         }
2834     }
2835 
2836     static boolean testIS_NEGATIVE(double a) {
2837         return bits(a)<0;
2838     }
2839 
2840     @Test(dataProvider = "doubleTestOpProvider")
2841     static void IS_NEGATIVEDouble64VectorTests(IntFunction<double[]> fa) {
2842         double[] a = fa.apply(SPECIES.length());
2843 
2844         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2845             for (int i = 0; i < a.length; i += SPECIES.length()) {
2846                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2847                 VectorMask<Double> mv = av.test(VectorOperators.IS_NEGATIVE);
2848 
2849                 // Check results as part of computation.
2850                 for (int j = 0; j < SPECIES.length(); j++) {
2851                     Assert.assertEquals(mv.laneIsSet(j), testIS_NEGATIVE(a[i + j]));
2852                 }
2853             }
2854         }
2855     }
2856 
2857     @Test(dataProvider = "doubleTestOpMaskProvider")
2858     static void IS_NEGATIVEMaskedDouble64VectorTests(IntFunction<double[]> fa,
2859                                           IntFunction<boolean[]> fm) {
2860         double[] a = fa.apply(SPECIES.length());
2861         boolean[] mask = fm.apply(SPECIES.length());
2862         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2863 
2864         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2865             for (int i = 0; i < a.length; i += SPECIES.length()) {
2866                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2867                 VectorMask<Double> mv = av.test(VectorOperators.IS_NEGATIVE, vmask);
2868 
2869                 // Check results as part of computation.
2870                 for (int j = 0; j < SPECIES.length(); j++) {
2871                     Assert.assertEquals(mv.laneIsSet(j),  vmask.laneIsSet(j) && testIS_NEGATIVE(a[i + j]));
2872                 }
2873             }
2874         }
2875     }
2876 
2877     static boolean testIS_FINITE(double a) {
2878         return Double.isFinite(a);
2879     }
2880 
2881     @Test(dataProvider = "doubleTestOpProvider")
2882     static void IS_FINITEDouble64VectorTests(IntFunction<double[]> fa) {
2883         double[] a = fa.apply(SPECIES.length());
2884 
2885         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2886             for (int i = 0; i < a.length; i += SPECIES.length()) {
2887                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2888                 VectorMask<Double> mv = av.test(VectorOperators.IS_FINITE);
2889 
2890                 // Check results as part of computation.
2891                 for (int j = 0; j < SPECIES.length(); j++) {
2892                     Assert.assertEquals(mv.laneIsSet(j), testIS_FINITE(a[i + j]));
2893                 }
2894             }
2895         }
2896     }
2897 
2898     @Test(dataProvider = "doubleTestOpMaskProvider")
2899     static void IS_FINITEMaskedDouble64VectorTests(IntFunction<double[]> fa,
2900                                           IntFunction<boolean[]> fm) {
2901         double[] a = fa.apply(SPECIES.length());
2902         boolean[] mask = fm.apply(SPECIES.length());
2903         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2904 
2905         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2906             for (int i = 0; i < a.length; i += SPECIES.length()) {
2907                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2908                 VectorMask<Double> mv = av.test(VectorOperators.IS_FINITE, vmask);
2909 
2910                 // Check results as part of computation.
2911                 for (int j = 0; j < SPECIES.length(); j++) {
2912                     Assert.assertEquals(mv.laneIsSet(j),  vmask.laneIsSet(j) && testIS_FINITE(a[i + j]));
2913                 }
2914             }
2915         }
2916     }
2917 
2918     static boolean testIS_NAN(double a) {
2919         return Double.isNaN(a);
2920     }
2921 
2922     @Test(dataProvider = "doubleTestOpProvider")
2923     static void IS_NANDouble64VectorTests(IntFunction<double[]> fa) {
2924         double[] a = fa.apply(SPECIES.length());
2925 
2926         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2927             for (int i = 0; i < a.length; i += SPECIES.length()) {
2928                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2929                 VectorMask<Double> mv = av.test(VectorOperators.IS_NAN);
2930 
2931                 // Check results as part of computation.
2932                 for (int j = 0; j < SPECIES.length(); j++) {
2933                     Assert.assertEquals(mv.laneIsSet(j), testIS_NAN(a[i + j]));
2934                 }
2935             }
2936         }
2937     }
2938 
2939     @Test(dataProvider = "doubleTestOpMaskProvider")
2940     static void IS_NANMaskedDouble64VectorTests(IntFunction<double[]> fa,
2941                                           IntFunction<boolean[]> fm) {
2942         double[] a = fa.apply(SPECIES.length());
2943         boolean[] mask = fm.apply(SPECIES.length());
2944         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2945 
2946         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2947             for (int i = 0; i < a.length; i += SPECIES.length()) {
2948                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2949                 VectorMask<Double> mv = av.test(VectorOperators.IS_NAN, vmask);
2950 
2951                 // Check results as part of computation.
2952                 for (int j = 0; j < SPECIES.length(); j++) {
2953                     Assert.assertEquals(mv.laneIsSet(j),  vmask.laneIsSet(j) && testIS_NAN(a[i + j]));
2954                 }
2955             }
2956         }
2957     }
2958 
2959     static boolean testIS_INFINITE(double a) {
2960         return Double.isInfinite(a);
2961     }
2962 
2963     @Test(dataProvider = "doubleTestOpProvider")
2964     static void IS_INFINITEDouble64VectorTests(IntFunction<double[]> fa) {
2965         double[] a = fa.apply(SPECIES.length());
2966 
2967         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2968             for (int i = 0; i < a.length; i += SPECIES.length()) {
2969                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2970                 VectorMask<Double> mv = av.test(VectorOperators.IS_INFINITE);
2971 
2972                 // Check results as part of computation.
2973                 for (int j = 0; j < SPECIES.length(); j++) {
2974                     Assert.assertEquals(mv.laneIsSet(j), testIS_INFINITE(a[i + j]));
2975                 }
2976             }
2977         }
2978     }
2979 
2980     @Test(dataProvider = "doubleTestOpMaskProvider")
2981     static void IS_INFINITEMaskedDouble64VectorTests(IntFunction<double[]> fa,
2982                                           IntFunction<boolean[]> fm) {
2983         double[] a = fa.apply(SPECIES.length());
2984         boolean[] mask = fm.apply(SPECIES.length());
2985         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
2986 
2987         for (int ic = 0; ic < INVOC_COUNT; ic++) {
2988             for (int i = 0; i < a.length; i += SPECIES.length()) {
2989                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
2990                 VectorMask<Double> mv = av.test(VectorOperators.IS_INFINITE, vmask);
2991 
2992                 // Check results as part of computation.
2993                 for (int j = 0; j < SPECIES.length(); j++) {
2994                     Assert.assertEquals(mv.laneIsSet(j),  vmask.laneIsSet(j) && testIS_INFINITE(a[i + j]));
2995                 }
2996             }
2997         }
2998     }
2999 
3000     @Test(dataProvider = "doubleCompareOpProvider")
3001     static void LTDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3002         double[] a = fa.apply(SPECIES.length());
3003         double[] b = fb.apply(SPECIES.length());
3004 
3005         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3006             for (int i = 0; i < a.length; i += SPECIES.length()) {
3007                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3008                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3009                 VectorMask<Double> mv = av.compare(VectorOperators.LT, bv);
3010 
3011                 // Check results as part of computation.
3012                 for (int j = 0; j < SPECIES.length(); j++) {
3013                     Assert.assertEquals(mv.laneIsSet(j), lt(a[i + j], b[i + j]));
3014                 }
3015             }
3016         }
3017     }
3018 
3019     @Test(dataProvider = "doubleCompareOpProvider")
3020     static void ltDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3021         double[] a = fa.apply(SPECIES.length());
3022         double[] b = fb.apply(SPECIES.length());
3023 
3024         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3025             for (int i = 0; i < a.length; i += SPECIES.length()) {
3026                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3027                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3028                 VectorMask<Double> mv = av.lt(bv);
3029 
3030                 // Check results as part of computation.
3031                 for (int j = 0; j < SPECIES.length(); j++) {
3032                     Assert.assertEquals(mv.laneIsSet(j), lt(a[i + j], b[i + j]));
3033                 }
3034             }
3035         }
3036     }
3037 
3038     @Test(dataProvider = "doubleCompareOpMaskProvider")
3039     static void LTDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
3040                                                 IntFunction<boolean[]> fm) {
3041         double[] a = fa.apply(SPECIES.length());
3042         double[] b = fb.apply(SPECIES.length());
3043         boolean[] mask = fm.apply(SPECIES.length());
3044 
3045         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3046 
3047         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3048             for (int i = 0; i < a.length; i += SPECIES.length()) {
3049                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3050                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3051                 VectorMask<Double> mv = av.compare(VectorOperators.LT, bv, vmask);
3052 
3053                 // Check results as part of computation.
3054                 for (int j = 0; j < SPECIES.length(); j++) {
3055                     Assert.assertEquals(mv.laneIsSet(j), mask[j] && lt(a[i + j], b[i + j]));
3056                 }
3057             }
3058         }
3059     }
3060 
3061     @Test(dataProvider = "doubleCompareOpProvider")
3062     static void GTDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3063         double[] a = fa.apply(SPECIES.length());
3064         double[] b = fb.apply(SPECIES.length());
3065 
3066         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3067             for (int i = 0; i < a.length; i += SPECIES.length()) {
3068                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3069                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3070                 VectorMask<Double> mv = av.compare(VectorOperators.GT, bv);
3071 
3072                 // Check results as part of computation.
3073                 for (int j = 0; j < SPECIES.length(); j++) {
3074                     Assert.assertEquals(mv.laneIsSet(j), gt(a[i + j], b[i + j]));
3075                 }
3076             }
3077         }
3078     }
3079 
3080     @Test(dataProvider = "doubleCompareOpMaskProvider")
3081     static void GTDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
3082                                                 IntFunction<boolean[]> fm) {
3083         double[] a = fa.apply(SPECIES.length());
3084         double[] b = fb.apply(SPECIES.length());
3085         boolean[] mask = fm.apply(SPECIES.length());
3086 
3087         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3088 
3089         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3090             for (int i = 0; i < a.length; i += SPECIES.length()) {
3091                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3092                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3093                 VectorMask<Double> mv = av.compare(VectorOperators.GT, bv, vmask);
3094 
3095                 // Check results as part of computation.
3096                 for (int j = 0; j < SPECIES.length(); j++) {
3097                     Assert.assertEquals(mv.laneIsSet(j), mask[j] && gt(a[i + j], b[i + j]));
3098                 }
3099             }
3100         }
3101     }
3102 
3103     @Test(dataProvider = "doubleCompareOpProvider")
3104     static void EQDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3105         double[] a = fa.apply(SPECIES.length());
3106         double[] b = fb.apply(SPECIES.length());
3107 
3108         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3109             for (int i = 0; i < a.length; i += SPECIES.length()) {
3110                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3111                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3112                 VectorMask<Double> mv = av.compare(VectorOperators.EQ, bv);
3113 
3114                 // Check results as part of computation.
3115                 for (int j = 0; j < SPECIES.length(); j++) {
3116                     Assert.assertEquals(mv.laneIsSet(j), eq(a[i + j], b[i + j]));
3117                 }
3118             }
3119         }
3120     }
3121 
3122     @Test(dataProvider = "doubleCompareOpProvider")
3123     static void eqDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3124         double[] a = fa.apply(SPECIES.length());
3125         double[] b = fb.apply(SPECIES.length());
3126 
3127         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3128             for (int i = 0; i < a.length; i += SPECIES.length()) {
3129                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3130                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3131                 VectorMask<Double> mv = av.eq(bv);
3132 
3133                 // Check results as part of computation.
3134                 for (int j = 0; j < SPECIES.length(); j++) {
3135                     Assert.assertEquals(mv.laneIsSet(j), eq(a[i + j], b[i + j]));
3136                 }
3137             }
3138         }
3139     }
3140 
3141     @Test(dataProvider = "doubleCompareOpMaskProvider")
3142     static void EQDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
3143                                                 IntFunction<boolean[]> fm) {
3144         double[] a = fa.apply(SPECIES.length());
3145         double[] b = fb.apply(SPECIES.length());
3146         boolean[] mask = fm.apply(SPECIES.length());
3147 
3148         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3149 
3150         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3151             for (int i = 0; i < a.length; i += SPECIES.length()) {
3152                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3153                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3154                 VectorMask<Double> mv = av.compare(VectorOperators.EQ, bv, vmask);
3155 
3156                 // Check results as part of computation.
3157                 for (int j = 0; j < SPECIES.length(); j++) {
3158                     Assert.assertEquals(mv.laneIsSet(j), mask[j] && eq(a[i + j], b[i + j]));
3159                 }
3160             }
3161         }
3162     }
3163 
3164     @Test(dataProvider = "doubleCompareOpProvider")
3165     static void NEDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3166         double[] a = fa.apply(SPECIES.length());
3167         double[] b = fb.apply(SPECIES.length());
3168 
3169         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3170             for (int i = 0; i < a.length; i += SPECIES.length()) {
3171                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3172                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3173                 VectorMask<Double> mv = av.compare(VectorOperators.NE, bv);
3174 
3175                 // Check results as part of computation.
3176                 for (int j = 0; j < SPECIES.length(); j++) {
3177                     Assert.assertEquals(mv.laneIsSet(j), neq(a[i + j], b[i + j]));
3178                 }
3179             }
3180         }
3181     }
3182 
3183     @Test(dataProvider = "doubleCompareOpMaskProvider")
3184     static void NEDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
3185                                                 IntFunction<boolean[]> fm) {
3186         double[] a = fa.apply(SPECIES.length());
3187         double[] b = fb.apply(SPECIES.length());
3188         boolean[] mask = fm.apply(SPECIES.length());
3189 
3190         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3191 
3192         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3193             for (int i = 0; i < a.length; i += SPECIES.length()) {
3194                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3195                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3196                 VectorMask<Double> mv = av.compare(VectorOperators.NE, bv, vmask);
3197 
3198                 // Check results as part of computation.
3199                 for (int j = 0; j < SPECIES.length(); j++) {
3200                     Assert.assertEquals(mv.laneIsSet(j), mask[j] && neq(a[i + j], b[i + j]));
3201                 }
3202             }
3203         }
3204     }
3205 
3206     @Test(dataProvider = "doubleCompareOpProvider")
3207     static void LEDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3208         double[] a = fa.apply(SPECIES.length());
3209         double[] b = fb.apply(SPECIES.length());
3210 
3211         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3212             for (int i = 0; i < a.length; i += SPECIES.length()) {
3213                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3214                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3215                 VectorMask<Double> mv = av.compare(VectorOperators.LE, bv);
3216 
3217                 // Check results as part of computation.
3218                 for (int j = 0; j < SPECIES.length(); j++) {
3219                     Assert.assertEquals(mv.laneIsSet(j), le(a[i + j], b[i + j]));
3220                 }
3221             }
3222         }
3223     }
3224 
3225     @Test(dataProvider = "doubleCompareOpMaskProvider")
3226     static void LEDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
3227                                                 IntFunction<boolean[]> fm) {
3228         double[] a = fa.apply(SPECIES.length());
3229         double[] b = fb.apply(SPECIES.length());
3230         boolean[] mask = fm.apply(SPECIES.length());
3231 
3232         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3233 
3234         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3235             for (int i = 0; i < a.length; i += SPECIES.length()) {
3236                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3237                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3238                 VectorMask<Double> mv = av.compare(VectorOperators.LE, bv, vmask);
3239 
3240                 // Check results as part of computation.
3241                 for (int j = 0; j < SPECIES.length(); j++) {
3242                     Assert.assertEquals(mv.laneIsSet(j), mask[j] && le(a[i + j], b[i + j]));
3243                 }
3244             }
3245         }
3246     }
3247 
3248     @Test(dataProvider = "doubleCompareOpProvider")
3249     static void GEDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3250         double[] a = fa.apply(SPECIES.length());
3251         double[] b = fb.apply(SPECIES.length());
3252 
3253         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3254             for (int i = 0; i < a.length; i += SPECIES.length()) {
3255                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3256                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3257                 VectorMask<Double> mv = av.compare(VectorOperators.GE, bv);
3258 
3259                 // Check results as part of computation.
3260                 for (int j = 0; j < SPECIES.length(); j++) {
3261                     Assert.assertEquals(mv.laneIsSet(j), ge(a[i + j], b[i + j]));
3262                 }
3263             }
3264         }
3265     }
3266 
3267     @Test(dataProvider = "doubleCompareOpMaskProvider")
3268     static void GEDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
3269                                                 IntFunction<boolean[]> fm) {
3270         double[] a = fa.apply(SPECIES.length());
3271         double[] b = fb.apply(SPECIES.length());
3272         boolean[] mask = fm.apply(SPECIES.length());
3273 
3274         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3275 
3276         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3277             for (int i = 0; i < a.length; i += SPECIES.length()) {
3278                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3279                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3280                 VectorMask<Double> mv = av.compare(VectorOperators.GE, bv, vmask);
3281 
3282                 // Check results as part of computation.
3283                 for (int j = 0; j < SPECIES.length(); j++) {
3284                     Assert.assertEquals(mv.laneIsSet(j), mask[j] && ge(a[i + j], b[i + j]));
3285                 }
3286             }
3287         }
3288     }
3289 
3290     @Test(dataProvider = "doubleCompareOpProvider")
3291     static void LTDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3292         double[] a = fa.apply(SPECIES.length());
3293         double[] b = fb.apply(SPECIES.length());
3294 
3295         for (int i = 0; i < a.length; i += SPECIES.length()) {
3296             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3297             VectorMask<Double> mv = av.compare(VectorOperators.LT, b[i]);
3298 
3299             // Check results as part of computation.
3300             for (int j = 0; j < SPECIES.length(); j++) {
3301                 Assert.assertEquals(mv.laneIsSet(j), a[i + j] < b[i]);
3302             }
3303         }
3304     }
3305 
3306     @Test(dataProvider = "doubleCompareOpMaskProvider")
3307     static void LTDouble64VectorTestsBroadcastMaskedSmokeTest(IntFunction<double[]> fa,
3308                                 IntFunction<double[]> fb, IntFunction<boolean[]> fm) {
3309         double[] a = fa.apply(SPECIES.length());
3310         double[] b = fb.apply(SPECIES.length());
3311         boolean[] mask = fm.apply(SPECIES.length());
3312 
3313         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3314 
3315         for (int i = 0; i < a.length; i += SPECIES.length()) {
3316             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3317             VectorMask<Double> mv = av.compare(VectorOperators.LT, b[i], vmask);
3318 
3319             // Check results as part of computation.
3320             for (int j = 0; j < SPECIES.length(); j++) {
3321                 Assert.assertEquals(mv.laneIsSet(j), mask[j] && (a[i + j] < b[i]));
3322             }
3323         }
3324     }
3325 
3326     @Test(dataProvider = "doubleCompareOpProvider")
3327     static void LTDouble64VectorTestsBroadcastLongSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3328         double[] a = fa.apply(SPECIES.length());
3329         double[] b = fb.apply(SPECIES.length());
3330 
3331         for (int i = 0; i < a.length; i += SPECIES.length()) {
3332             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3333             VectorMask<Double> mv = av.compare(VectorOperators.LT, (long)b[i]);
3334 
3335             // Check results as part of computation.
3336             for (int j = 0; j < SPECIES.length(); j++) {
3337                 Assert.assertEquals(mv.laneIsSet(j), a[i + j] < (double)((long)b[i]));
3338             }
3339         }
3340     }
3341 
3342     @Test(dataProvider = "doubleCompareOpMaskProvider")
3343     static void LTDouble64VectorTestsBroadcastLongMaskedSmokeTest(IntFunction<double[]> fa,
3344                                 IntFunction<double[]> fb, IntFunction<boolean[]> fm) {
3345         double[] a = fa.apply(SPECIES.length());
3346         double[] b = fb.apply(SPECIES.length());
3347         boolean[] mask = fm.apply(SPECIES.length());
3348 
3349         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3350 
3351         for (int i = 0; i < a.length; i += SPECIES.length()) {
3352             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3353             VectorMask<Double> mv = av.compare(VectorOperators.LT, (long)b[i], vmask);
3354 
3355             // Check results as part of computation.
3356             for (int j = 0; j < SPECIES.length(); j++) {
3357                 Assert.assertEquals(mv.laneIsSet(j), mask[j] && (a[i + j] < (double)((long)b[i])));
3358             }
3359         }
3360     }
3361 
3362     @Test(dataProvider = "doubleCompareOpProvider")
3363     static void EQDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3364         double[] a = fa.apply(SPECIES.length());
3365         double[] b = fb.apply(SPECIES.length());
3366 
3367         for (int i = 0; i < a.length; i += SPECIES.length()) {
3368             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3369             VectorMask<Double> mv = av.compare(VectorOperators.EQ, b[i]);
3370 
3371             // Check results as part of computation.
3372             for (int j = 0; j < SPECIES.length(); j++) {
3373                 Assert.assertEquals(mv.laneIsSet(j), a[i + j] == b[i]);
3374             }
3375         }
3376     }
3377 
3378     @Test(dataProvider = "doubleCompareOpMaskProvider")
3379     static void EQDouble64VectorTestsBroadcastMaskedSmokeTest(IntFunction<double[]> fa,
3380                                 IntFunction<double[]> fb, IntFunction<boolean[]> fm) {
3381         double[] a = fa.apply(SPECIES.length());
3382         double[] b = fb.apply(SPECIES.length());
3383         boolean[] mask = fm.apply(SPECIES.length());
3384 
3385         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3386 
3387         for (int i = 0; i < a.length; i += SPECIES.length()) {
3388             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3389             VectorMask<Double> mv = av.compare(VectorOperators.EQ, b[i], vmask);
3390 
3391             // Check results as part of computation.
3392             for (int j = 0; j < SPECIES.length(); j++) {
3393                 Assert.assertEquals(mv.laneIsSet(j), mask[j] && (a[i + j] == b[i]));
3394             }
3395         }
3396     }
3397 
3398     @Test(dataProvider = "doubleCompareOpProvider")
3399     static void EQDouble64VectorTestsBroadcastLongSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3400         double[] a = fa.apply(SPECIES.length());
3401         double[] b = fb.apply(SPECIES.length());
3402 
3403         for (int i = 0; i < a.length; i += SPECIES.length()) {
3404             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3405             VectorMask<Double> mv = av.compare(VectorOperators.EQ, (long)b[i]);
3406 
3407             // Check results as part of computation.
3408             for (int j = 0; j < SPECIES.length(); j++) {
3409                 Assert.assertEquals(mv.laneIsSet(j), a[i + j] == (double)((long)b[i]));
3410             }
3411         }
3412     }
3413 
3414     @Test(dataProvider = "doubleCompareOpMaskProvider")
3415     static void EQDouble64VectorTestsBroadcastLongMaskedSmokeTest(IntFunction<double[]> fa,
3416                                 IntFunction<double[]> fb, IntFunction<boolean[]> fm) {
3417         double[] a = fa.apply(SPECIES.length());
3418         double[] b = fb.apply(SPECIES.length());
3419         boolean[] mask = fm.apply(SPECIES.length());
3420 
3421         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3422 
3423         for (int i = 0; i < a.length; i += SPECIES.length()) {
3424             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3425             VectorMask<Double> mv = av.compare(VectorOperators.EQ, (long)b[i], vmask);
3426 
3427             // Check results as part of computation.
3428             for (int j = 0; j < SPECIES.length(); j++) {
3429                 Assert.assertEquals(mv.laneIsSet(j), mask[j] && (a[i + j] == (double)((long)b[i])));
3430             }
3431         }
3432     }
3433 
3434     static double blend(double a, double b, boolean mask) {
3435         return mask ? b : a;
3436     }
3437 
3438     @Test(dataProvider = "doubleBinaryOpMaskProvider")
3439     static void blendDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb,
3440                                           IntFunction<boolean[]> fm) {
3441         double[] a = fa.apply(SPECIES.length());
3442         double[] b = fb.apply(SPECIES.length());
3443         double[] r = fr.apply(SPECIES.length());
3444         boolean[] mask = fm.apply(SPECIES.length());
3445         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3446 
3447         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3448             for (int i = 0; i < a.length; i += SPECIES.length()) {
3449                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3450                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3451                 av.blend(bv, vmask).intoArray(r, i);
3452             }
3453         }
3454 
3455         assertArraysEquals(r, a, b, mask, Double64VectorTests::blend);
3456     }
3457 
3458     @Test(dataProvider = "doubleUnaryOpShuffleProvider")
3459     static void RearrangeDouble64VectorTests(IntFunction<double[]> fa,
3460                                            BiFunction<Integer,Integer,int[]> fs) {
3461         double[] a = fa.apply(SPECIES.length());
3462         int[] order = fs.apply(a.length, SPECIES.length());
3463         double[] r = fr.apply(SPECIES.length());
3464 
3465         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3466             for (int i = 0; i < a.length; i += SPECIES.length()) {
3467                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3468                 av.rearrange(VectorShuffle.fromArray(SPECIES, order, i)).intoArray(r, i);
3469             }
3470         }
3471 
3472         assertRearrangeArraysEquals(r, a, order, SPECIES.length());
3473     }
3474 
3475     @Test(dataProvider = "doubleUnaryOpShuffleMaskProvider")
3476     static void RearrangeDouble64VectorTestsMaskedSmokeTest(IntFunction<double[]> fa,
3477                                                           BiFunction<Integer,Integer,int[]> fs,
3478                                                           IntFunction<boolean[]> fm) {
3479         double[] a = fa.apply(SPECIES.length());
3480         int[] order = fs.apply(a.length, SPECIES.length());
3481         double[] r = fr.apply(SPECIES.length());
3482         boolean[] mask = fm.apply(SPECIES.length());
3483         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3484 
3485         for (int i = 0; i < a.length; i += SPECIES.length()) {
3486             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3487             av.rearrange(VectorShuffle.fromArray(SPECIES, order, i), vmask).intoArray(r, i);
3488         }
3489 
3490         assertRearrangeArraysEquals(r, a, order, mask, SPECIES.length());
3491     }
3492 
3493     @Test(dataProvider = "doubleUnaryOpMaskProvider")
3494     static void compressDouble64VectorTests(IntFunction<double[]> fa,
3495                                                 IntFunction<boolean[]> fm) {
3496         double[] a = fa.apply(SPECIES.length());
3497         double[] r = fr.apply(SPECIES.length());
3498         boolean[] mask = fm.apply(SPECIES.length());
3499         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3500 
3501         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3502             for (int i = 0; i < a.length; i += SPECIES.length()) {
3503                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3504                 av.compress(vmask).intoArray(r, i);
3505             }
3506         }
3507 
3508         assertcompressArraysEquals(r, a, mask, SPECIES.length());
3509     }
3510 
3511     @Test(dataProvider = "doubleUnaryOpMaskProvider")
3512     static void expandDouble64VectorTests(IntFunction<double[]> fa,
3513                                                 IntFunction<boolean[]> fm) {
3514         double[] a = fa.apply(SPECIES.length());
3515         double[] r = fr.apply(SPECIES.length());
3516         boolean[] mask = fm.apply(SPECIES.length());
3517         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3518 
3519         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3520             for (int i = 0; i < a.length; i += SPECIES.length()) {
3521                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3522                 av.expand(vmask).intoArray(r, i);
3523             }
3524         }
3525 
3526         assertexpandArraysEquals(r, a, mask, SPECIES.length());
3527     }
3528 
3529     @Test(dataProvider = "doubleUnaryOpProvider")
3530     static void getDouble64VectorTests(IntFunction<double[]> fa) {
3531         double[] a = fa.apply(SPECIES.length());
3532         double[] r = fr.apply(SPECIES.length());
3533 
3534         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3535             for (int i = 0; i < a.length; i += SPECIES.length()) {
3536                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3537                 int num_lanes = SPECIES.length();
3538                 // Manually unroll because full unroll happens after intrinsification.
3539                 // Unroll is needed because get intrinsic requires for index to be a known constant.
3540                 if (num_lanes == 1) {
3541                     r[i]=av.lane(0);
3542                 } else if (num_lanes == 2) {
3543                     r[i]=av.lane(0);
3544                     r[i+1]=av.lane(1);
3545                 } else if (num_lanes == 4) {
3546                     r[i]=av.lane(0);
3547                     r[i+1]=av.lane(1);
3548                     r[i+2]=av.lane(2);
3549                     r[i+3]=av.lane(3);
3550                 } else if (num_lanes == 8) {
3551                     r[i]=av.lane(0);
3552                     r[i+1]=av.lane(1);
3553                     r[i+2]=av.lane(2);
3554                     r[i+3]=av.lane(3);
3555                     r[i+4]=av.lane(4);
3556                     r[i+5]=av.lane(5);
3557                     r[i+6]=av.lane(6);
3558                     r[i+7]=av.lane(7);
3559                 } else if (num_lanes == 16) {
3560                     r[i]=av.lane(0);
3561                     r[i+1]=av.lane(1);
3562                     r[i+2]=av.lane(2);
3563                     r[i+3]=av.lane(3);
3564                     r[i+4]=av.lane(4);
3565                     r[i+5]=av.lane(5);
3566                     r[i+6]=av.lane(6);
3567                     r[i+7]=av.lane(7);
3568                     r[i+8]=av.lane(8);
3569                     r[i+9]=av.lane(9);
3570                     r[i+10]=av.lane(10);
3571                     r[i+11]=av.lane(11);
3572                     r[i+12]=av.lane(12);
3573                     r[i+13]=av.lane(13);
3574                     r[i+14]=av.lane(14);
3575                     r[i+15]=av.lane(15);
3576                 } else if (num_lanes == 32) {
3577                     r[i]=av.lane(0);
3578                     r[i+1]=av.lane(1);
3579                     r[i+2]=av.lane(2);
3580                     r[i+3]=av.lane(3);
3581                     r[i+4]=av.lane(4);
3582                     r[i+5]=av.lane(5);
3583                     r[i+6]=av.lane(6);
3584                     r[i+7]=av.lane(7);
3585                     r[i+8]=av.lane(8);
3586                     r[i+9]=av.lane(9);
3587                     r[i+10]=av.lane(10);
3588                     r[i+11]=av.lane(11);
3589                     r[i+12]=av.lane(12);
3590                     r[i+13]=av.lane(13);
3591                     r[i+14]=av.lane(14);
3592                     r[i+15]=av.lane(15);
3593                     r[i+16]=av.lane(16);
3594                     r[i+17]=av.lane(17);
3595                     r[i+18]=av.lane(18);
3596                     r[i+19]=av.lane(19);
3597                     r[i+20]=av.lane(20);
3598                     r[i+21]=av.lane(21);
3599                     r[i+22]=av.lane(22);
3600                     r[i+23]=av.lane(23);
3601                     r[i+24]=av.lane(24);
3602                     r[i+25]=av.lane(25);
3603                     r[i+26]=av.lane(26);
3604                     r[i+27]=av.lane(27);
3605                     r[i+28]=av.lane(28);
3606                     r[i+29]=av.lane(29);
3607                     r[i+30]=av.lane(30);
3608                     r[i+31]=av.lane(31);
3609                 } else if (num_lanes == 64) {
3610                     r[i]=av.lane(0);
3611                     r[i+1]=av.lane(1);
3612                     r[i+2]=av.lane(2);
3613                     r[i+3]=av.lane(3);
3614                     r[i+4]=av.lane(4);
3615                     r[i+5]=av.lane(5);
3616                     r[i+6]=av.lane(6);
3617                     r[i+7]=av.lane(7);
3618                     r[i+8]=av.lane(8);
3619                     r[i+9]=av.lane(9);
3620                     r[i+10]=av.lane(10);
3621                     r[i+11]=av.lane(11);
3622                     r[i+12]=av.lane(12);
3623                     r[i+13]=av.lane(13);
3624                     r[i+14]=av.lane(14);
3625                     r[i+15]=av.lane(15);
3626                     r[i+16]=av.lane(16);
3627                     r[i+17]=av.lane(17);
3628                     r[i+18]=av.lane(18);
3629                     r[i+19]=av.lane(19);
3630                     r[i+20]=av.lane(20);
3631                     r[i+21]=av.lane(21);
3632                     r[i+22]=av.lane(22);
3633                     r[i+23]=av.lane(23);
3634                     r[i+24]=av.lane(24);
3635                     r[i+25]=av.lane(25);
3636                     r[i+26]=av.lane(26);
3637                     r[i+27]=av.lane(27);
3638                     r[i+28]=av.lane(28);
3639                     r[i+29]=av.lane(29);
3640                     r[i+30]=av.lane(30);
3641                     r[i+31]=av.lane(31);
3642                     r[i+32]=av.lane(32);
3643                     r[i+33]=av.lane(33);
3644                     r[i+34]=av.lane(34);
3645                     r[i+35]=av.lane(35);
3646                     r[i+36]=av.lane(36);
3647                     r[i+37]=av.lane(37);
3648                     r[i+38]=av.lane(38);
3649                     r[i+39]=av.lane(39);
3650                     r[i+40]=av.lane(40);
3651                     r[i+41]=av.lane(41);
3652                     r[i+42]=av.lane(42);
3653                     r[i+43]=av.lane(43);
3654                     r[i+44]=av.lane(44);
3655                     r[i+45]=av.lane(45);
3656                     r[i+46]=av.lane(46);
3657                     r[i+47]=av.lane(47);
3658                     r[i+48]=av.lane(48);
3659                     r[i+49]=av.lane(49);
3660                     r[i+50]=av.lane(50);
3661                     r[i+51]=av.lane(51);
3662                     r[i+52]=av.lane(52);
3663                     r[i+53]=av.lane(53);
3664                     r[i+54]=av.lane(54);
3665                     r[i+55]=av.lane(55);
3666                     r[i+56]=av.lane(56);
3667                     r[i+57]=av.lane(57);
3668                     r[i+58]=av.lane(58);
3669                     r[i+59]=av.lane(59);
3670                     r[i+60]=av.lane(60);
3671                     r[i+61]=av.lane(61);
3672                     r[i+62]=av.lane(62);
3673                     r[i+63]=av.lane(63);
3674                 } else {
3675                     for (int j = 0; j < SPECIES.length(); j++) {
3676                         r[i+j]=av.lane(j);
3677                     }
3678                 }
3679             }
3680         }
3681 
3682         assertArraysStrictlyEquals(r, a);
3683     }
3684 
3685     @Test(dataProvider = "doubleUnaryOpProvider")
3686     static void BroadcastDouble64VectorTests(IntFunction<double[]> fa) {
3687         double[] a = fa.apply(SPECIES.length());
3688         double[] r = new double[a.length];
3689 
3690         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3691             for (int i = 0; i < a.length; i += SPECIES.length()) {
3692                 DoubleVector.broadcast(SPECIES, a[i]).intoArray(r, i);
3693             }
3694         }
3695 
3696         assertBroadcastArraysEquals(r, a);
3697     }
3698 
3699     @Test(dataProvider = "doubleUnaryOpProvider")
3700     static void ZeroDouble64VectorTests(IntFunction<double[]> fa) {
3701         double[] a = fa.apply(SPECIES.length());
3702         double[] r = new double[a.length];
3703 
3704         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3705             for (int i = 0; i < a.length; i += SPECIES.length()) {
3706                 DoubleVector.zero(SPECIES).intoArray(a, i);
3707             }
3708         }
3709 
3710         Assert.assertEquals(a, r);
3711     }
3712 
3713     static double[] sliceUnary(double[] a, int origin, int idx) {
3714         double[] res = new double[SPECIES.length()];
3715         for (int i = 0; i < SPECIES.length(); i++){
3716             if(i+origin < SPECIES.length())
3717                 res[i] = a[idx+i+origin];
3718             else
3719                 res[i] = (double)0;
3720         }
3721         return res;
3722     }
3723 
3724     @Test(dataProvider = "doubleUnaryOpProvider")
3725     static void sliceUnaryDouble64VectorTests(IntFunction<double[]> fa) {
3726         double[] a = fa.apply(SPECIES.length());
3727         double[] r = new double[a.length];
3728         int origin = RAND.nextInt(SPECIES.length());
3729         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3730             for (int i = 0; i < a.length; i += SPECIES.length()) {
3731                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3732                 av.slice(origin).intoArray(r, i);
3733             }
3734         }
3735 
3736         assertArraysEquals(r, a, origin, Double64VectorTests::sliceUnary);
3737     }
3738 
3739     static double[] sliceBinary(double[] a, double[] b, int origin, int idx) {
3740         double[] res = new double[SPECIES.length()];
3741         for (int i = 0, j = 0; i < SPECIES.length(); i++){
3742             if(i+origin < SPECIES.length())
3743                 res[i] = a[idx+i+origin];
3744             else {
3745                 res[i] = b[idx+j];
3746                 j++;
3747             }
3748         }
3749         return res;
3750     }
3751 
3752     @Test(dataProvider = "doubleBinaryOpProvider")
3753     static void sliceBinaryDouble64VectorTestsBinary(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3754         double[] a = fa.apply(SPECIES.length());
3755         double[] b = fb.apply(SPECIES.length());
3756         double[] r = new double[a.length];
3757         int origin = RAND.nextInt(SPECIES.length());
3758         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3759             for (int i = 0; i < a.length; i += SPECIES.length()) {
3760                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3761                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3762                 av.slice(origin, bv).intoArray(r, i);
3763             }
3764         }
3765 
3766         assertArraysEquals(r, a, b, origin, Double64VectorTests::sliceBinary);
3767     }
3768 
3769     static double[] slice(double[] a, double[] b, int origin, boolean[] mask, int idx) {
3770         double[] res = new double[SPECIES.length()];
3771         for (int i = 0, j = 0; i < SPECIES.length(); i++){
3772             if(i+origin < SPECIES.length())
3773                 res[i] = mask[i] ? a[idx+i+origin] : (double)0;
3774             else {
3775                 res[i] = mask[i] ? b[idx+j] : (double)0;
3776                 j++;
3777             }
3778         }
3779         return res;
3780     }
3781 
3782     @Test(dataProvider = "doubleBinaryOpMaskProvider")
3783     static void sliceDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
3784     IntFunction<boolean[]> fm) {
3785         double[] a = fa.apply(SPECIES.length());
3786         double[] b = fb.apply(SPECIES.length());
3787         boolean[] mask = fm.apply(SPECIES.length());
3788         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3789 
3790         double[] r = new double[a.length];
3791         int origin = RAND.nextInt(SPECIES.length());
3792         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3793             for (int i = 0; i < a.length; i += SPECIES.length()) {
3794                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3795                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3796                 av.slice(origin, bv, vmask).intoArray(r, i);
3797             }
3798         }
3799 
3800         assertArraysEquals(r, a, b, origin, mask, Double64VectorTests::slice);
3801     }
3802 
3803     static double[] unsliceUnary(double[] a, int origin, int idx) {
3804         double[] res = new double[SPECIES.length()];
3805         for (int i = 0, j = 0; i < SPECIES.length(); i++){
3806             if(i < origin)
3807                 res[i] = (double)0;
3808             else {
3809                 res[i] = a[idx+j];
3810                 j++;
3811             }
3812         }
3813         return res;
3814     }
3815 
3816     @Test(dataProvider = "doubleUnaryOpProvider")
3817     static void unsliceUnaryDouble64VectorTests(IntFunction<double[]> fa) {
3818         double[] a = fa.apply(SPECIES.length());
3819         double[] r = new double[a.length];
3820         int origin = RAND.nextInt(SPECIES.length());
3821         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3822             for (int i = 0; i < a.length; i += SPECIES.length()) {
3823                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3824                 av.unslice(origin).intoArray(r, i);
3825             }
3826         }
3827 
3828         assertArraysEquals(r, a, origin, Double64VectorTests::unsliceUnary);
3829     }
3830 
3831     static double[] unsliceBinary(double[] a, double[] b, int origin, int part, int idx) {
3832         double[] res = new double[SPECIES.length()];
3833         for (int i = 0, j = 0; i < SPECIES.length(); i++){
3834             if (part == 0) {
3835                 if (i < origin)
3836                     res[i] = b[idx+i];
3837                 else {
3838                     res[i] = a[idx+j];
3839                     j++;
3840                 }
3841             } else if (part == 1) {
3842                 if (i < origin)
3843                     res[i] = a[idx+SPECIES.length()-origin+i];
3844                 else {
3845                     res[i] = b[idx+origin+j];
3846                     j++;
3847                 }
3848             }
3849         }
3850         return res;
3851     }
3852 
3853     @Test(dataProvider = "doubleBinaryOpProvider")
3854     static void unsliceBinaryDouble64VectorTestsBinary(IntFunction<double[]> fa, IntFunction<double[]> fb) {
3855         double[] a = fa.apply(SPECIES.length());
3856         double[] b = fb.apply(SPECIES.length());
3857         double[] r = new double[a.length];
3858         int origin = RAND.nextInt(SPECIES.length());
3859         int part = RAND.nextInt(2);
3860         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3861             for (int i = 0; i < a.length; i += SPECIES.length()) {
3862                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3863                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3864                 av.unslice(origin, bv, part).intoArray(r, i);
3865             }
3866         }
3867 
3868         assertArraysEquals(r, a, b, origin, part, Double64VectorTests::unsliceBinary);
3869     }
3870 
3871     static double[] unslice(double[] a, double[] b, int origin, int part, boolean[] mask, int idx) {
3872         double[] res = new double[SPECIES.length()];
3873         for (int i = 0, j = 0; i < SPECIES.length(); i++){
3874             if(i+origin < SPECIES.length())
3875                 res[i] = b[idx+i+origin];
3876             else {
3877                 res[i] = b[idx+j];
3878                 j++;
3879             }
3880         }
3881         for (int i = 0; i < SPECIES.length(); i++){
3882             res[i] = mask[i] ? a[idx+i] : res[i];
3883         }
3884         double[] res1 = new double[SPECIES.length()];
3885         if (part == 0) {
3886             for (int i = 0, j = 0; i < SPECIES.length(); i++){
3887                 if (i < origin)
3888                     res1[i] = b[idx+i];
3889                 else {
3890                    res1[i] = res[j];
3891                    j++;
3892                 }
3893             }
3894         } else if (part == 1) {
3895             for (int i = 0, j = 0; i < SPECIES.length(); i++){
3896                 if (i < origin)
3897                     res1[i] = res[SPECIES.length()-origin+i];
3898                 else {
3899                     res1[i] = b[idx+origin+j];
3900                     j++;
3901                 }
3902             }
3903         }
3904         return res1;
3905     }
3906 
3907     @Test(dataProvider = "doubleBinaryOpMaskProvider")
3908     static void unsliceDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
3909     IntFunction<boolean[]> fm) {
3910         double[] a = fa.apply(SPECIES.length());
3911         double[] b = fb.apply(SPECIES.length());
3912         boolean[] mask = fm.apply(SPECIES.length());
3913         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
3914         double[] r = new double[a.length];
3915         int origin = RAND.nextInt(SPECIES.length());
3916         int part = RAND.nextInt(2);
3917         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3918             for (int i = 0; i < a.length; i += SPECIES.length()) {
3919                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3920                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
3921                 av.unslice(origin, bv, part, vmask).intoArray(r, i);
3922             }
3923         }
3924 
3925         assertArraysEquals(r, a, b, origin, part, mask, Double64VectorTests::unslice);
3926     }
3927 
3928     static double SIN(double a) {
3929         return (double)(Math.sin((double)a));
3930     }
3931 
3932     static double strictSIN(double a) {
3933         return (double)(StrictMath.sin((double)a));
3934     }
3935 
3936     @Test(dataProvider = "doubleUnaryOpProvider")
3937     static void SINDouble64VectorTests(IntFunction<double[]> fa) {
3938         double[] a = fa.apply(SPECIES.length());
3939         double[] r = fr.apply(SPECIES.length());
3940 
3941         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3942             for (int i = 0; i < a.length; i += SPECIES.length()) {
3943                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3944                 av.lanewise(VectorOperators.SIN).intoArray(r, i);
3945             }
3946         }
3947 
3948         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::SIN, Double64VectorTests::strictSIN);
3949     }
3950 
3951     static double EXP(double a) {
3952         return (double)(Math.exp((double)a));
3953     }
3954 
3955     static double strictEXP(double a) {
3956         return (double)(StrictMath.exp((double)a));
3957     }
3958 
3959     @Test(dataProvider = "doubleUnaryOpProvider")
3960     static void EXPDouble64VectorTests(IntFunction<double[]> fa) {
3961         double[] a = fa.apply(SPECIES.length());
3962         double[] r = fr.apply(SPECIES.length());
3963 
3964         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3965             for (int i = 0; i < a.length; i += SPECIES.length()) {
3966                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3967                 av.lanewise(VectorOperators.EXP).intoArray(r, i);
3968             }
3969         }
3970 
3971         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::EXP, Double64VectorTests::strictEXP);
3972     }
3973 
3974     static double LOG1P(double a) {
3975         return (double)(Math.log1p((double)a));
3976     }
3977 
3978     static double strictLOG1P(double a) {
3979         return (double)(StrictMath.log1p((double)a));
3980     }
3981 
3982     @Test(dataProvider = "doubleUnaryOpProvider")
3983     static void LOG1PDouble64VectorTests(IntFunction<double[]> fa) {
3984         double[] a = fa.apply(SPECIES.length());
3985         double[] r = fr.apply(SPECIES.length());
3986 
3987         for (int ic = 0; ic < INVOC_COUNT; ic++) {
3988             for (int i = 0; i < a.length; i += SPECIES.length()) {
3989                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
3990                 av.lanewise(VectorOperators.LOG1P).intoArray(r, i);
3991             }
3992         }
3993 
3994         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::LOG1P, Double64VectorTests::strictLOG1P);
3995     }
3996 
3997     static double LOG(double a) {
3998         return (double)(Math.log((double)a));
3999     }
4000 
4001     static double strictLOG(double a) {
4002         return (double)(StrictMath.log((double)a));
4003     }
4004 
4005     @Test(dataProvider = "doubleUnaryOpProvider")
4006     static void LOGDouble64VectorTests(IntFunction<double[]> fa) {
4007         double[] a = fa.apply(SPECIES.length());
4008         double[] r = fr.apply(SPECIES.length());
4009 
4010         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4011             for (int i = 0; i < a.length; i += SPECIES.length()) {
4012                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4013                 av.lanewise(VectorOperators.LOG).intoArray(r, i);
4014             }
4015         }
4016 
4017         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::LOG, Double64VectorTests::strictLOG);
4018     }
4019 
4020     static double LOG10(double a) {
4021         return (double)(Math.log10((double)a));
4022     }
4023 
4024     static double strictLOG10(double a) {
4025         return (double)(StrictMath.log10((double)a));
4026     }
4027 
4028     @Test(dataProvider = "doubleUnaryOpProvider")
4029     static void LOG10Double64VectorTests(IntFunction<double[]> fa) {
4030         double[] a = fa.apply(SPECIES.length());
4031         double[] r = fr.apply(SPECIES.length());
4032 
4033         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4034             for (int i = 0; i < a.length; i += SPECIES.length()) {
4035                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4036                 av.lanewise(VectorOperators.LOG10).intoArray(r, i);
4037             }
4038         }
4039 
4040         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::LOG10, Double64VectorTests::strictLOG10);
4041     }
4042 
4043     static double EXPM1(double a) {
4044         return (double)(Math.expm1((double)a));
4045     }
4046 
4047     static double strictEXPM1(double a) {
4048         return (double)(StrictMath.expm1((double)a));
4049     }
4050 
4051     @Test(dataProvider = "doubleUnaryOpProvider")
4052     static void EXPM1Double64VectorTests(IntFunction<double[]> fa) {
4053         double[] a = fa.apply(SPECIES.length());
4054         double[] r = fr.apply(SPECIES.length());
4055 
4056         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4057             for (int i = 0; i < a.length; i += SPECIES.length()) {
4058                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4059                 av.lanewise(VectorOperators.EXPM1).intoArray(r, i);
4060             }
4061         }
4062 
4063         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::EXPM1, Double64VectorTests::strictEXPM1);
4064     }
4065 
4066     static double COS(double a) {
4067         return (double)(Math.cos((double)a));
4068     }
4069 
4070     static double strictCOS(double a) {
4071         return (double)(StrictMath.cos((double)a));
4072     }
4073 
4074     @Test(dataProvider = "doubleUnaryOpProvider")
4075     static void COSDouble64VectorTests(IntFunction<double[]> fa) {
4076         double[] a = fa.apply(SPECIES.length());
4077         double[] r = fr.apply(SPECIES.length());
4078 
4079         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4080             for (int i = 0; i < a.length; i += SPECIES.length()) {
4081                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4082                 av.lanewise(VectorOperators.COS).intoArray(r, i);
4083             }
4084         }
4085 
4086         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::COS, Double64VectorTests::strictCOS);
4087     }
4088 
4089     static double TAN(double a) {
4090         return (double)(Math.tan((double)a));
4091     }
4092 
4093     static double strictTAN(double a) {
4094         return (double)(StrictMath.tan((double)a));
4095     }
4096 
4097     @Test(dataProvider = "doubleUnaryOpProvider")
4098     static void TANDouble64VectorTests(IntFunction<double[]> fa) {
4099         double[] a = fa.apply(SPECIES.length());
4100         double[] r = fr.apply(SPECIES.length());
4101 
4102         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4103             for (int i = 0; i < a.length; i += SPECIES.length()) {
4104                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4105                 av.lanewise(VectorOperators.TAN).intoArray(r, i);
4106             }
4107         }
4108 
4109         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::TAN, Double64VectorTests::strictTAN);
4110     }
4111 
4112     static double SINH(double a) {
4113         return (double)(Math.sinh((double)a));
4114     }
4115 
4116     static double strictSINH(double a) {
4117         return (double)(StrictMath.sinh((double)a));
4118     }
4119 
4120     @Test(dataProvider = "doubleUnaryOpProvider")
4121     static void SINHDouble64VectorTests(IntFunction<double[]> fa) {
4122         double[] a = fa.apply(SPECIES.length());
4123         double[] r = fr.apply(SPECIES.length());
4124 
4125         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4126             for (int i = 0; i < a.length; i += SPECIES.length()) {
4127                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4128                 av.lanewise(VectorOperators.SINH).intoArray(r, i);
4129             }
4130         }
4131 
4132         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::SINH, Double64VectorTests::strictSINH);
4133     }
4134 
4135     static double COSH(double a) {
4136         return (double)(Math.cosh((double)a));
4137     }
4138 
4139     static double strictCOSH(double a) {
4140         return (double)(StrictMath.cosh((double)a));
4141     }
4142 
4143     @Test(dataProvider = "doubleUnaryOpProvider")
4144     static void COSHDouble64VectorTests(IntFunction<double[]> fa) {
4145         double[] a = fa.apply(SPECIES.length());
4146         double[] r = fr.apply(SPECIES.length());
4147 
4148         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4149             for (int i = 0; i < a.length; i += SPECIES.length()) {
4150                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4151                 av.lanewise(VectorOperators.COSH).intoArray(r, i);
4152             }
4153         }
4154 
4155         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::COSH, Double64VectorTests::strictCOSH);
4156     }
4157 
4158     static double TANH(double a) {
4159         return (double)(Math.tanh((double)a));
4160     }
4161 
4162     static double strictTANH(double a) {
4163         return (double)(StrictMath.tanh((double)a));
4164     }
4165 
4166     @Test(dataProvider = "doubleUnaryOpProvider")
4167     static void TANHDouble64VectorTests(IntFunction<double[]> fa) {
4168         double[] a = fa.apply(SPECIES.length());
4169         double[] r = fr.apply(SPECIES.length());
4170 
4171         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4172             for (int i = 0; i < a.length; i += SPECIES.length()) {
4173                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4174                 av.lanewise(VectorOperators.TANH).intoArray(r, i);
4175             }
4176         }
4177 
4178         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::TANH, Double64VectorTests::strictTANH);
4179     }
4180 
4181     static double ASIN(double a) {
4182         return (double)(Math.asin((double)a));
4183     }
4184 
4185     static double strictASIN(double a) {
4186         return (double)(StrictMath.asin((double)a));
4187     }
4188 
4189     @Test(dataProvider = "doubleUnaryOpProvider")
4190     static void ASINDouble64VectorTests(IntFunction<double[]> fa) {
4191         double[] a = fa.apply(SPECIES.length());
4192         double[] r = fr.apply(SPECIES.length());
4193 
4194         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4195             for (int i = 0; i < a.length; i += SPECIES.length()) {
4196                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4197                 av.lanewise(VectorOperators.ASIN).intoArray(r, i);
4198             }
4199         }
4200 
4201         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::ASIN, Double64VectorTests::strictASIN);
4202     }
4203 
4204     static double ACOS(double a) {
4205         return (double)(Math.acos((double)a));
4206     }
4207 
4208     static double strictACOS(double a) {
4209         return (double)(StrictMath.acos((double)a));
4210     }
4211 
4212     @Test(dataProvider = "doubleUnaryOpProvider")
4213     static void ACOSDouble64VectorTests(IntFunction<double[]> fa) {
4214         double[] a = fa.apply(SPECIES.length());
4215         double[] r = fr.apply(SPECIES.length());
4216 
4217         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4218             for (int i = 0; i < a.length; i += SPECIES.length()) {
4219                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4220                 av.lanewise(VectorOperators.ACOS).intoArray(r, i);
4221             }
4222         }
4223 
4224         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::ACOS, Double64VectorTests::strictACOS);
4225     }
4226 
4227     static double ATAN(double a) {
4228         return (double)(Math.atan((double)a));
4229     }
4230 
4231     static double strictATAN(double a) {
4232         return (double)(StrictMath.atan((double)a));
4233     }
4234 
4235     @Test(dataProvider = "doubleUnaryOpProvider")
4236     static void ATANDouble64VectorTests(IntFunction<double[]> fa) {
4237         double[] a = fa.apply(SPECIES.length());
4238         double[] r = fr.apply(SPECIES.length());
4239 
4240         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4241             for (int i = 0; i < a.length; i += SPECIES.length()) {
4242                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4243                 av.lanewise(VectorOperators.ATAN).intoArray(r, i);
4244             }
4245         }
4246 
4247         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::ATAN, Double64VectorTests::strictATAN);
4248     }
4249 
4250     static double CBRT(double a) {
4251         return (double)(Math.cbrt((double)a));
4252     }
4253 
4254     static double strictCBRT(double a) {
4255         return (double)(StrictMath.cbrt((double)a));
4256     }
4257 
4258     @Test(dataProvider = "doubleUnaryOpProvider")
4259     static void CBRTDouble64VectorTests(IntFunction<double[]> fa) {
4260         double[] a = fa.apply(SPECIES.length());
4261         double[] r = fr.apply(SPECIES.length());
4262 
4263         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4264             for (int i = 0; i < a.length; i += SPECIES.length()) {
4265                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4266                 av.lanewise(VectorOperators.CBRT).intoArray(r, i);
4267             }
4268         }
4269 
4270         assertArraysEqualsWithinOneUlp(r, a, Double64VectorTests::CBRT, Double64VectorTests::strictCBRT);
4271     }
4272 
4273     static double HYPOT(double a, double b) {
4274         return (double)(Math.hypot((double)a, (double)b));
4275     }
4276 
4277     static double strictHYPOT(double a, double b) {
4278         return (double)(StrictMath.hypot((double)a, (double)b));
4279     }
4280 
4281     @Test(dataProvider = "doubleBinaryOpProvider")
4282     static void HYPOTDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
4283         double[] a = fa.apply(SPECIES.length());
4284         double[] b = fb.apply(SPECIES.length());
4285         double[] r = fr.apply(SPECIES.length());
4286 
4287         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4288             for (int i = 0; i < a.length; i += SPECIES.length()) {
4289                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4290                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
4291                 av.lanewise(VectorOperators.HYPOT, bv).intoArray(r, i);
4292             }
4293         }
4294 
4295         assertArraysEqualsWithinOneUlp(r, a, b, Double64VectorTests::HYPOT, Double64VectorTests::strictHYPOT);
4296     }
4297 
4298 
4299     static double POW(double a, double b) {
4300         return (double)(Math.pow((double)a, (double)b));
4301     }
4302 
4303     static double strictPOW(double a, double b) {
4304         return (double)(StrictMath.pow((double)a, (double)b));
4305     }
4306 
4307     @Test(dataProvider = "doubleBinaryOpProvider")
4308     static void POWDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
4309         double[] a = fa.apply(SPECIES.length());
4310         double[] b = fb.apply(SPECIES.length());
4311         double[] r = fr.apply(SPECIES.length());
4312 
4313         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4314             for (int i = 0; i < a.length; i += SPECIES.length()) {
4315                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4316                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
4317                 av.lanewise(VectorOperators.POW, bv).intoArray(r, i);
4318             }
4319         }
4320 
4321         assertArraysEqualsWithinOneUlp(r, a, b, Double64VectorTests::POW, Double64VectorTests::strictPOW);
4322     }
4323 
4324 
4325     static double pow(double a, double b) {
4326         return (double)(Math.pow((double)a, (double)b));
4327     }
4328 
4329     static double strictpow(double a, double b) {
4330         return (double)(StrictMath.pow((double)a, (double)b));
4331     }
4332 
4333     @Test(dataProvider = "doubleBinaryOpProvider")
4334     static void powDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
4335         double[] a = fa.apply(SPECIES.length());
4336         double[] b = fb.apply(SPECIES.length());
4337         double[] r = fr.apply(SPECIES.length());
4338 
4339         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4340             for (int i = 0; i < a.length; i += SPECIES.length()) {
4341                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4342                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
4343                 av.pow(bv).intoArray(r, i);
4344             }
4345         }
4346 
4347         assertArraysEqualsWithinOneUlp(r, a, b, Double64VectorTests::pow, Double64VectorTests::strictpow);
4348     }
4349 
4350 
4351     static double ATAN2(double a, double b) {
4352         return (double)(Math.atan2((double)a, (double)b));
4353     }
4354 
4355     static double strictATAN2(double a, double b) {
4356         return (double)(StrictMath.atan2((double)a, (double)b));
4357     }
4358 
4359     @Test(dataProvider = "doubleBinaryOpProvider")
4360     static void ATAN2Double64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb) {
4361         double[] a = fa.apply(SPECIES.length());
4362         double[] b = fb.apply(SPECIES.length());
4363         double[] r = fr.apply(SPECIES.length());
4364 
4365         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4366             for (int i = 0; i < a.length; i += SPECIES.length()) {
4367                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4368                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
4369                 av.lanewise(VectorOperators.ATAN2, bv).intoArray(r, i);
4370             }
4371         }
4372 
4373         assertArraysEqualsWithinOneUlp(r, a, b, Double64VectorTests::ATAN2, Double64VectorTests::strictATAN2);
4374     }
4375 
4376 
4377     @Test(dataProvider = "doubleBinaryOpProvider")
4378     static void POWDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
4379         double[] a = fa.apply(SPECIES.length());
4380         double[] b = fb.apply(SPECIES.length());
4381         double[] r = fr.apply(SPECIES.length());
4382 
4383         for (int i = 0; i < a.length; i += SPECIES.length()) {
4384             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4385             av.lanewise(VectorOperators.POW, b[i]).intoArray(r, i);
4386         }
4387 
4388         assertBroadcastArraysEqualsWithinOneUlp(r, a, b, Double64VectorTests::POW, Double64VectorTests::strictPOW);
4389     }
4390 
4391 
4392     @Test(dataProvider = "doubleBinaryOpProvider")
4393     static void powDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
4394         double[] a = fa.apply(SPECIES.length());
4395         double[] b = fb.apply(SPECIES.length());
4396         double[] r = fr.apply(SPECIES.length());
4397 
4398         for (int i = 0; i < a.length; i += SPECIES.length()) {
4399             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4400             av.pow(b[i]).intoArray(r, i);
4401         }
4402 
4403         assertBroadcastArraysEqualsWithinOneUlp(r, a, b, Double64VectorTests::pow, Double64VectorTests::strictpow);
4404     }
4405 
4406 
4407     static double FMA(double a, double b, double c) {
4408         return (double)(Math.fma(a, b, c));
4409     }
4410 
4411     static double fma(double a, double b, double c) {
4412         return (double)(Math.fma(a, b, c));
4413     }
4414 
4415     @Test(dataProvider = "doubleTernaryOpProvider")
4416     static void FMADouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb, IntFunction<double[]> fc) {
4417         int count = INVOC_COUNT;
4418         switch ("FMA") {
4419         case "fma": case "lanewise_FMA":
4420            // Math.fma uses BigDecimal
4421            count = Math.max(5, count/20); break;
4422         }
4423         final int INVOC_COUNT = count;
4424         double[] a = fa.apply(SPECIES.length());
4425         double[] b = fb.apply(SPECIES.length());
4426         double[] c = fc.apply(SPECIES.length());
4427         double[] r = fr.apply(SPECIES.length());
4428 
4429         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4430             for (int i = 0; i < a.length; i += SPECIES.length()) {
4431                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4432                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
4433                 DoubleVector cv = DoubleVector.fromArray(SPECIES, c, i);
4434                 av.lanewise(VectorOperators.FMA, bv, cv).intoArray(r, i);
4435             }
4436         }
4437 
4438         assertArraysEquals(r, a, b, c, Double64VectorTests::FMA);
4439     }
4440 
4441     @Test(dataProvider = "doubleTernaryOpProvider")
4442     static void fmaDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb, IntFunction<double[]> fc) {
4443         int count = INVOC_COUNT;
4444         switch ("fma") {
4445         case "fma": case "lanewise_FMA":
4446            // Math.fma uses BigDecimal
4447            count = Math.max(5, count/20); break;
4448         }
4449         final int INVOC_COUNT = count;
4450         double[] a = fa.apply(SPECIES.length());
4451         double[] b = fb.apply(SPECIES.length());
4452         double[] c = fc.apply(SPECIES.length());
4453         double[] r = fr.apply(SPECIES.length());
4454 
4455         for (int i = 0; i < a.length; i += SPECIES.length()) {
4456             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4457             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
4458             DoubleVector cv = DoubleVector.fromArray(SPECIES, c, i);
4459             av.fma(bv, cv).intoArray(r, i);
4460         }
4461 
4462         assertArraysEquals(r, a, b, c, Double64VectorTests::fma);
4463     }
4464 
4465     @Test(dataProvider = "doubleTernaryOpMaskProvider")
4466     static void FMADouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<double[]> fb,
4467                                           IntFunction<double[]> fc, IntFunction<boolean[]> fm) {
4468         int count = INVOC_COUNT;
4469         switch ("FMA") {
4470         case "fma": case "lanewise_FMA":
4471            // Math.fma uses BigDecimal
4472            count = Math.max(5, count/20); break;
4473         }
4474         final int INVOC_COUNT = count;
4475         double[] a = fa.apply(SPECIES.length());
4476         double[] b = fb.apply(SPECIES.length());
4477         double[] c = fc.apply(SPECIES.length());
4478         double[] r = fr.apply(SPECIES.length());
4479         boolean[] mask = fm.apply(SPECIES.length());
4480         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
4481 
4482         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4483             for (int i = 0; i < a.length; i += SPECIES.length()) {
4484                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4485                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
4486                 DoubleVector cv = DoubleVector.fromArray(SPECIES, c, i);
4487                 av.lanewise(VectorOperators.FMA, bv, cv, vmask).intoArray(r, i);
4488             }
4489         }
4490 
4491         assertArraysEquals(r, a, b, c, mask, Double64VectorTests::FMA);
4492     }
4493 
4494     @Test(dataProvider = "doubleTernaryOpProvider")
4495     static void FMADouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb, IntFunction<double[]> fc) {
4496         double[] a = fa.apply(SPECIES.length());
4497         double[] b = fb.apply(SPECIES.length());
4498         double[] c = fc.apply(SPECIES.length());
4499         double[] r = fr.apply(SPECIES.length());
4500 
4501         for (int i = 0; i < a.length; i += SPECIES.length()) {
4502             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4503             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
4504             av.lanewise(VectorOperators.FMA, bv, c[i]).intoArray(r, i);
4505         }
4506         assertBroadcastArraysEquals(r, a, b, c, Double64VectorTests::FMA);
4507     }
4508 
4509     @Test(dataProvider = "doubleTernaryOpProvider")
4510     static void FMADouble64VectorTestsAltBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb, IntFunction<double[]> fc) {
4511         double[] a = fa.apply(SPECIES.length());
4512         double[] b = fb.apply(SPECIES.length());
4513         double[] c = fc.apply(SPECIES.length());
4514         double[] r = fr.apply(SPECIES.length());
4515 
4516         for (int i = 0; i < a.length; i += SPECIES.length()) {
4517             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4518             DoubleVector cv = DoubleVector.fromArray(SPECIES, c, i);
4519             av.lanewise(VectorOperators.FMA, b[i], cv).intoArray(r, i);
4520         }
4521         assertAltBroadcastArraysEquals(r, a, b, c, Double64VectorTests::FMA);
4522     }
4523 
4524     @Test(dataProvider = "doubleTernaryOpMaskProvider")
4525     static void FMADouble64VectorTestsBroadcastMaskedSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb,
4526                                           IntFunction<double[]> fc, IntFunction<boolean[]> fm) {
4527         double[] a = fa.apply(SPECIES.length());
4528         double[] b = fb.apply(SPECIES.length());
4529         double[] c = fc.apply(SPECIES.length());
4530         double[] r = fr.apply(SPECIES.length());
4531         boolean[] mask = fm.apply(SPECIES.length());
4532         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
4533 
4534         for (int i = 0; i < a.length; i += SPECIES.length()) {
4535             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4536             DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
4537             av.lanewise(VectorOperators.FMA, bv, c[i], vmask).intoArray(r, i);
4538         }
4539 
4540         assertBroadcastArraysEquals(r, a, b, c, mask, Double64VectorTests::FMA);
4541     }
4542 
4543     @Test(dataProvider = "doubleTernaryOpMaskProvider")
4544     static void FMADouble64VectorTestsAltBroadcastMaskedSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb,
4545                                           IntFunction<double[]> fc, IntFunction<boolean[]> fm) {
4546         double[] a = fa.apply(SPECIES.length());
4547         double[] b = fb.apply(SPECIES.length());
4548         double[] c = fc.apply(SPECIES.length());
4549         double[] r = fr.apply(SPECIES.length());
4550         boolean[] mask = fm.apply(SPECIES.length());
4551         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
4552 
4553         for (int i = 0; i < a.length; i += SPECIES.length()) {
4554             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4555             DoubleVector cv = DoubleVector.fromArray(SPECIES, c, i);
4556             av.lanewise(VectorOperators.FMA, b[i], cv, vmask).intoArray(r, i);
4557         }
4558 
4559         assertAltBroadcastArraysEquals(r, a, b, c, mask, Double64VectorTests::FMA);
4560     }
4561 
4562     @Test(dataProvider = "doubleTernaryOpProvider")
4563     static void FMADouble64VectorTestsDoubleBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb, IntFunction<double[]> fc) {
4564         int count = INVOC_COUNT;
4565         switch ("FMA") {
4566         case "fma": case "lanewise_FMA":
4567            // Math.fma uses BigDecimal
4568            count = Math.max(5, count/20); break;
4569         }
4570         final int INVOC_COUNT = count;
4571         double[] a = fa.apply(SPECIES.length());
4572         double[] b = fb.apply(SPECIES.length());
4573         double[] c = fc.apply(SPECIES.length());
4574         double[] r = fr.apply(SPECIES.length());
4575 
4576         for (int i = 0; i < a.length; i += SPECIES.length()) {
4577             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4578             av.lanewise(VectorOperators.FMA, b[i], c[i]).intoArray(r, i);
4579         }
4580 
4581         assertDoubleBroadcastArraysEquals(r, a, b, c, Double64VectorTests::FMA);
4582     }
4583 
4584     @Test(dataProvider = "doubleTernaryOpProvider")
4585     static void fmaDouble64VectorTestsDoubleBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb, IntFunction<double[]> fc) {
4586         int count = INVOC_COUNT;
4587         switch ("fma") {
4588         case "fma": case "lanewise_FMA":
4589            // Math.fma uses BigDecimal
4590            count = Math.max(5, count/20); break;
4591         }
4592         final int INVOC_COUNT = count;
4593         double[] a = fa.apply(SPECIES.length());
4594         double[] b = fb.apply(SPECIES.length());
4595         double[] c = fc.apply(SPECIES.length());
4596         double[] r = fr.apply(SPECIES.length());
4597 
4598         for (int i = 0; i < a.length; i += SPECIES.length()) {
4599             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4600             av.fma(b[i], c[i]).intoArray(r, i);
4601         }
4602 
4603         assertDoubleBroadcastArraysEquals(r, a, b, c, Double64VectorTests::fma);
4604     }
4605 
4606     @Test(dataProvider = "doubleTernaryOpMaskProvider")
4607     static void FMADouble64VectorTestsDoubleBroadcastMaskedSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb,
4608                                           IntFunction<double[]> fc, IntFunction<boolean[]> fm) {
4609         int count = INVOC_COUNT;
4610         switch ("FMA") {
4611         case "fma": case "lanewise_FMA":
4612            // Math.fma uses BigDecimal
4613            count = Math.max(5, count/20); break;
4614         }
4615         final int INVOC_COUNT = count;
4616         double[] a = fa.apply(SPECIES.length());
4617         double[] b = fb.apply(SPECIES.length());
4618         double[] c = fc.apply(SPECIES.length());
4619         double[] r = fr.apply(SPECIES.length());
4620         boolean[] mask = fm.apply(SPECIES.length());
4621         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
4622 
4623         for (int i = 0; i < a.length; i += SPECIES.length()) {
4624             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4625             av.lanewise(VectorOperators.FMA, b[i], c[i], vmask).intoArray(r, i);
4626         }
4627 
4628         assertDoubleBroadcastArraysEquals(r, a, b, c, mask, Double64VectorTests::FMA);
4629     }
4630 
4631     static double NEG(double a) {
4632         return (double)(-((double)a));
4633     }
4634 
4635     static double neg(double a) {
4636         return (double)(-((double)a));
4637     }
4638 
4639     @Test(dataProvider = "doubleUnaryOpProvider")
4640     static void NEGDouble64VectorTests(IntFunction<double[]> fa) {
4641         double[] a = fa.apply(SPECIES.length());
4642         double[] r = fr.apply(SPECIES.length());
4643 
4644         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4645             for (int i = 0; i < a.length; i += SPECIES.length()) {
4646                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4647                 av.lanewise(VectorOperators.NEG).intoArray(r, i);
4648             }
4649         }
4650 
4651         assertArraysEquals(r, a, Double64VectorTests::NEG);
4652     }
4653 
4654     @Test(dataProvider = "doubleUnaryOpProvider")
4655     static void negDouble64VectorTests(IntFunction<double[]> fa) {
4656         double[] a = fa.apply(SPECIES.length());
4657         double[] r = fr.apply(SPECIES.length());
4658 
4659         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4660             for (int i = 0; i < a.length; i += SPECIES.length()) {
4661                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4662                 av.neg().intoArray(r, i);
4663             }
4664         }
4665 
4666         assertArraysEquals(r, a, Double64VectorTests::neg);
4667     }
4668 
4669     @Test(dataProvider = "doubleUnaryOpMaskProvider")
4670     static void NEGMaskedDouble64VectorTests(IntFunction<double[]> fa,
4671                                                 IntFunction<boolean[]> fm) {
4672         double[] a = fa.apply(SPECIES.length());
4673         double[] r = fr.apply(SPECIES.length());
4674         boolean[] mask = fm.apply(SPECIES.length());
4675         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
4676 
4677         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4678             for (int i = 0; i < a.length; i += SPECIES.length()) {
4679                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4680                 av.lanewise(VectorOperators.NEG, vmask).intoArray(r, i);
4681             }
4682         }
4683 
4684         assertArraysEquals(r, a, mask, Double64VectorTests::NEG);
4685     }
4686 
4687     static double ABS(double a) {
4688         return (double)(Math.abs((double)a));
4689     }
4690 
4691     static double abs(double a) {
4692         return (double)(Math.abs((double)a));
4693     }
4694 
4695     @Test(dataProvider = "doubleUnaryOpProvider")
4696     static void ABSDouble64VectorTests(IntFunction<double[]> fa) {
4697         double[] a = fa.apply(SPECIES.length());
4698         double[] r = fr.apply(SPECIES.length());
4699 
4700         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4701             for (int i = 0; i < a.length; i += SPECIES.length()) {
4702                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4703                 av.lanewise(VectorOperators.ABS).intoArray(r, i);
4704             }
4705         }
4706 
4707         assertArraysEquals(r, a, Double64VectorTests::ABS);
4708     }
4709 
4710     @Test(dataProvider = "doubleUnaryOpProvider")
4711     static void absDouble64VectorTests(IntFunction<double[]> fa) {
4712         double[] a = fa.apply(SPECIES.length());
4713         double[] r = fr.apply(SPECIES.length());
4714 
4715         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4716             for (int i = 0; i < a.length; i += SPECIES.length()) {
4717                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4718                 av.abs().intoArray(r, i);
4719             }
4720         }
4721 
4722         assertArraysEquals(r, a, Double64VectorTests::abs);
4723     }
4724 
4725     @Test(dataProvider = "doubleUnaryOpMaskProvider")
4726     static void ABSMaskedDouble64VectorTests(IntFunction<double[]> fa,
4727                                                 IntFunction<boolean[]> fm) {
4728         double[] a = fa.apply(SPECIES.length());
4729         double[] r = fr.apply(SPECIES.length());
4730         boolean[] mask = fm.apply(SPECIES.length());
4731         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
4732 
4733         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4734             for (int i = 0; i < a.length; i += SPECIES.length()) {
4735                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4736                 av.lanewise(VectorOperators.ABS, vmask).intoArray(r, i);
4737             }
4738         }
4739 
4740         assertArraysEquals(r, a, mask, Double64VectorTests::ABS);
4741     }
4742 
4743     static double SQRT(double a) {
4744         return (double)(Math.sqrt((double)a));
4745     }
4746 
4747     static double sqrt(double a) {
4748         return (double)(Math.sqrt((double)a));
4749     }
4750 
4751     @Test(dataProvider = "doubleUnaryOpProvider")
4752     static void SQRTDouble64VectorTests(IntFunction<double[]> fa) {
4753         double[] a = fa.apply(SPECIES.length());
4754         double[] r = fr.apply(SPECIES.length());
4755 
4756         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4757             for (int i = 0; i < a.length; i += SPECIES.length()) {
4758                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4759                 av.lanewise(VectorOperators.SQRT).intoArray(r, i);
4760             }
4761         }
4762 
4763         assertArraysEquals(r, a, Double64VectorTests::SQRT);
4764     }
4765 
4766     @Test(dataProvider = "doubleUnaryOpProvider")
4767     static void sqrtDouble64VectorTests(IntFunction<double[]> fa) {
4768         double[] a = fa.apply(SPECIES.length());
4769         double[] r = fr.apply(SPECIES.length());
4770 
4771         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4772             for (int i = 0; i < a.length; i += SPECIES.length()) {
4773                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4774                 av.sqrt().intoArray(r, i);
4775             }
4776         }
4777 
4778         assertArraysEquals(r, a, Double64VectorTests::sqrt);
4779     }
4780 
4781     @Test(dataProvider = "doubleUnaryOpMaskProvider")
4782     static void SQRTMaskedDouble64VectorTests(IntFunction<double[]> fa,
4783                                                 IntFunction<boolean[]> fm) {
4784         double[] a = fa.apply(SPECIES.length());
4785         double[] r = fr.apply(SPECIES.length());
4786         boolean[] mask = fm.apply(SPECIES.length());
4787         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
4788 
4789         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4790             for (int i = 0; i < a.length; i += SPECIES.length()) {
4791                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4792                 av.lanewise(VectorOperators.SQRT, vmask).intoArray(r, i);
4793             }
4794         }
4795 
4796         assertArraysEquals(r, a, mask, Double64VectorTests::SQRT);
4797     }
4798 
4799     @Test(dataProvider = "doubleCompareOpProvider")
4800     static void ltDouble64VectorTestsBroadcastSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
4801         double[] a = fa.apply(SPECIES.length());
4802         double[] b = fb.apply(SPECIES.length());
4803 
4804         for (int i = 0; i < a.length; i += SPECIES.length()) {
4805             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4806             VectorMask<Double> mv = av.lt(b[i]);
4807 
4808             // Check results as part of computation.
4809             for (int j = 0; j < SPECIES.length(); j++) {
4810                 Assert.assertEquals(mv.laneIsSet(j), a[i + j] < b[i]);
4811             }
4812         }
4813     }
4814 
4815     @Test(dataProvider = "doubleCompareOpProvider")
4816     static void eqDouble64VectorTestsBroadcastMaskedSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb) {
4817         double[] a = fa.apply(SPECIES.length());
4818         double[] b = fb.apply(SPECIES.length());
4819 
4820         for (int i = 0; i < a.length; i += SPECIES.length()) {
4821             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4822             VectorMask<Double> mv = av.eq(b[i]);
4823 
4824             // Check results as part of computation.
4825             for (int j = 0; j < SPECIES.length(); j++) {
4826                 Assert.assertEquals(mv.laneIsSet(j), a[i + j] == b[i]);
4827             }
4828         }
4829     }
4830 
4831     @Test(dataProvider = "doubletoIntUnaryOpProvider")
4832     static void toIntArrayDouble64VectorTestsSmokeTest(IntFunction<double[]> fa) {
4833         double[] a = fa.apply(SPECIES.length());
4834 
4835         for (int i = 0; i < a.length; i += SPECIES.length()) {
4836             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4837             int[] r = av.toIntArray();
4838             assertArraysEquals(r, a, i);
4839         }
4840     }
4841 
4842     @Test(dataProvider = "doubletoLongUnaryOpProvider")
4843     static void toLongArrayDouble64VectorTestsSmokeTest(IntFunction<double[]> fa) {
4844         double[] a = fa.apply(SPECIES.length());
4845 
4846         for (int i = 0; i < a.length; i += SPECIES.length()) {
4847             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4848             long[] r = av.toLongArray();
4849             assertArraysEquals(r, a, i);
4850         }
4851     }
4852 
4853 
4854     @Test(dataProvider = "doubleUnaryOpProvider")
4855     static void toStringDouble64VectorTestsSmokeTest(IntFunction<double[]> fa) {
4856         double[] a = fa.apply(SPECIES.length());
4857 
4858         for (int i = 0; i < a.length; i += SPECIES.length()) {
4859             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4860             String str = av.toString();
4861 
4862             double subarr[] = Arrays.copyOfRange(a, i, i + SPECIES.length());
4863             Assert.assertTrue(str.equals(Arrays.toString(subarr)), "at index " + i + ", string should be = " + Arrays.toString(subarr) + ", but is = " + str);
4864         }
4865     }
4866 
4867     @Test(dataProvider = "doubleUnaryOpProvider")
4868     static void hashCodeDouble64VectorTestsSmokeTest(IntFunction<double[]> fa) {
4869         double[] a = fa.apply(SPECIES.length());
4870 
4871         for (int i = 0; i < a.length; i += SPECIES.length()) {
4872             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4873             int hash = av.hashCode();
4874 
4875             double subarr[] = Arrays.copyOfRange(a, i, i + SPECIES.length());
4876             int expectedHash = Objects.hash(SPECIES, Arrays.hashCode(subarr));
4877             Assert.assertTrue(hash == expectedHash, "at index " + i + ", hash should be = " + expectedHash + ", but is = " + hash);
4878         }
4879     }
4880 
4881 
4882     static long ADDReduceLong(double[] a, int idx) {
4883         double res = 0;
4884         for (int i = idx; i < (idx + SPECIES.length()); i++) {
4885             res += a[i];
4886         }
4887 
4888         return (long)res;
4889     }
4890 
4891     static long ADDReduceAllLong(double[] a) {
4892         long res = 0;
4893         for (int i = 0; i < a.length; i += SPECIES.length()) {
4894             res += ADDReduceLong(a, i);
4895         }
4896 
4897         return res;
4898     }
4899 
4900     @Test(dataProvider = "doubleUnaryOpProvider")
4901     static void ADDReduceLongDouble64VectorTests(IntFunction<double[]> fa) {
4902         double[] a = fa.apply(SPECIES.length());
4903         long[] r = lfr.apply(SPECIES.length());
4904         long ra = 0;
4905 
4906         for (int i = 0; i < a.length; i += SPECIES.length()) {
4907             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4908             r[i] = av.reduceLanesToLong(VectorOperators.ADD);
4909         }
4910 
4911         ra = 0;
4912         for (int i = 0; i < a.length; i ++) {
4913             ra += r[i];
4914         }
4915 
4916         assertReductionLongArraysEquals(r, ra, a,
4917                 Double64VectorTests::ADDReduceLong, Double64VectorTests::ADDReduceAllLong);
4918     }
4919 
4920     static long ADDReduceLongMasked(double[] a, int idx, boolean[] mask) {
4921         double res = 0;
4922         for (int i = idx; i < (idx + SPECIES.length()); i++) {
4923             if(mask[i % SPECIES.length()])
4924                 res += a[i];
4925         }
4926 
4927         return (long)res;
4928     }
4929 
4930     static long ADDReduceAllLongMasked(double[] a, boolean[] mask) {
4931         long res = 0;
4932         for (int i = 0; i < a.length; i += SPECIES.length()) {
4933             res += ADDReduceLongMasked(a, i, mask);
4934         }
4935 
4936         return res;
4937     }
4938 
4939     @Test(dataProvider = "doubleUnaryOpMaskProvider")
4940     static void ADDReduceLongDouble64VectorTestsMasked(IntFunction<double[]> fa, IntFunction<boolean[]> fm) {
4941         double[] a = fa.apply(SPECIES.length());
4942         long[] r = lfr.apply(SPECIES.length());
4943         boolean[] mask = fm.apply(SPECIES.length());
4944         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
4945         long ra = 0;
4946 
4947         for (int i = 0; i < a.length; i += SPECIES.length()) {
4948             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4949             r[i] = av.reduceLanesToLong(VectorOperators.ADD, vmask);
4950         }
4951 
4952         ra = 0;
4953         for (int i = 0; i < a.length; i ++) {
4954             ra += r[i];
4955         }
4956 
4957         assertReductionLongArraysEqualsMasked(r, ra, a, mask,
4958                 Double64VectorTests::ADDReduceLongMasked, Double64VectorTests::ADDReduceAllLongMasked);
4959     }
4960 
4961     @Test(dataProvider = "doubletoLongUnaryOpProvider")
4962     static void BroadcastLongDouble64VectorTestsSmokeTest(IntFunction<double[]> fa) {
4963         double[] a = fa.apply(SPECIES.length());
4964         double[] r = new double[a.length];
4965 
4966         for (int i = 0; i < a.length; i += SPECIES.length()) {
4967             DoubleVector.broadcast(SPECIES, (long)a[i]).intoArray(r, i);
4968         }
4969         assertBroadcastArraysEquals(r, a);
4970     }
4971 
4972     @Test(dataProvider = "doubleBinaryOpMaskProvider")
4973     static void blendDouble64VectorTestsBroadcastLongSmokeTest(IntFunction<double[]> fa, IntFunction<double[]> fb,
4974                                           IntFunction<boolean[]> fm) {
4975         double[] a = fa.apply(SPECIES.length());
4976         double[] b = fb.apply(SPECIES.length());
4977         double[] r = fr.apply(SPECIES.length());
4978         boolean[] mask = fm.apply(SPECIES.length());
4979         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
4980 
4981         for (int ic = 0; ic < INVOC_COUNT; ic++) {
4982             for (int i = 0; i < a.length; i += SPECIES.length()) {
4983                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
4984                 av.blend((long)b[i], vmask).intoArray(r, i);
4985             }
4986         }
4987         assertBroadcastLongArraysEquals(r, a, b, mask, Double64VectorTests::blend);
4988     }
4989 
4990 
4991     @Test(dataProvider = "doubleUnaryOpSelectFromProvider")
4992     static void SelectFromDouble64VectorTests(IntFunction<double[]> fa,
4993                                            BiFunction<Integer,Integer,double[]> fs) {
4994         double[] a = fa.apply(SPECIES.length());
4995         double[] order = fs.apply(a.length, SPECIES.length());
4996         double[] r = fr.apply(SPECIES.length());
4997 
4998         for (int i = 0; i < a.length; i += SPECIES.length()) {
4999             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
5000             DoubleVector bv = DoubleVector.fromArray(SPECIES, order, i);
5001             bv.selectFrom(av).intoArray(r, i);
5002         }
5003 
5004         assertSelectFromArraysEquals(r, a, order, SPECIES.length());
5005     }
5006 
5007     @Test(dataProvider = "doubleSelectFromTwoVectorOpProvider")
5008     static void SelectFromTwoVectorDouble64VectorTests(IntFunction<double[]> fa, IntFunction<double[]> fb, IntFunction<double[]> fc) {
5009         double[] a = fa.apply(SPECIES.length());
5010         double[] b = fb.apply(SPECIES.length());
5011         double[] idx = fc.apply(SPECIES.length());
5012         double[] r = fr.apply(SPECIES.length());
5013 
5014         for (int ic = 0; ic < INVOC_COUNT; ic++) {
5015             for (int i = 0; i < idx.length; i += SPECIES.length()) {
5016                 DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
5017                 DoubleVector bv = DoubleVector.fromArray(SPECIES, b, i);
5018                 DoubleVector idxv = DoubleVector.fromArray(SPECIES, idx, i);
5019                 idxv.selectFrom(av, bv).intoArray(r, i);
5020             }
5021         }
5022         assertSelectFromTwoVectorEquals(r, idx, a, b, SPECIES.length());
5023     }
5024 
5025     @Test(dataProvider = "doubleUnaryOpSelectFromMaskProvider")
5026     static void SelectFromDouble64VectorTestsMaskedSmokeTest(IntFunction<double[]> fa,
5027                                                            BiFunction<Integer,Integer,double[]> fs,
5028                                                            IntFunction<boolean[]> fm) {
5029         double[] a = fa.apply(SPECIES.length());
5030         double[] order = fs.apply(a.length, SPECIES.length());
5031         double[] r = fr.apply(SPECIES.length());
5032         boolean[] mask = fm.apply(SPECIES.length());
5033         VectorMask<Double> vmask = VectorMask.fromArray(SPECIES, mask, 0);
5034 
5035         for (int i = 0; i < a.length; i += SPECIES.length()) {
5036             DoubleVector av = DoubleVector.fromArray(SPECIES, a, i);
5037             DoubleVector bv = DoubleVector.fromArray(SPECIES, order, i);
5038             bv.selectFrom(av, vmask).intoArray(r, i);
5039         }
5040 
5041         assertSelectFromArraysEquals(r, a, order, mask, SPECIES.length());
5042     }
5043 
5044     @Test(dataProvider = "shuffleProvider")
5045     static void shuffleMiscellaneousDouble64VectorTestsSmokeTest(BiFunction<Integer,Integer,int[]> fs) {
5046         int[] a = fs.apply(SPECIES.length() * BUFFER_REPS, SPECIES.length());
5047 
5048         for (int i = 0; i < a.length; i += SPECIES.length()) {
5049             var shuffle = VectorShuffle.fromArray(SPECIES, a, i);
5050             int hash = shuffle.hashCode();
5051             int length = shuffle.length();
5052 
5053             int subarr[] = Arrays.copyOfRange(a, i, i + SPECIES.length());
5054             int expectedHash = Objects.hash(SPECIES, Arrays.hashCode(subarr));
5055             Assert.assertTrue(hash == expectedHash, "at index " + i + ", hash should be = " + expectedHash + ", but is = " + hash);
5056             Assert.assertEquals(length, SPECIES.length());
5057         }
5058     }
5059 
5060     @Test(dataProvider = "shuffleProvider")
5061     static void shuffleToStringDouble64VectorTestsSmokeTest(BiFunction<Integer,Integer,int[]> fs) {
5062         int[] a = fs.apply(SPECIES.length() * BUFFER_REPS, SPECIES.length());
5063 
5064         for (int i = 0; i < a.length; i += SPECIES.length()) {
5065             var shuffle = VectorShuffle.fromArray(SPECIES, a, i);
5066             String str = shuffle.toString();
5067 
5068             int subarr[] = Arrays.copyOfRange(a, i, i + SPECIES.length());
5069             Assert.assertTrue(str.equals("Shuffle" + Arrays.toString(subarr)), "at index " +
5070                 i + ", string should be = " + Arrays.toString(subarr) + ", but is = " + str);
5071         }
5072     }
5073 
5074     @Test(dataProvider = "shuffleCompareOpProvider")
5075     static void shuffleEqualsDouble64VectorTestsSmokeTest(BiFunction<Integer,Integer,int[]> fa, BiFunction<Integer,Integer,int[]> fb) {
5076         int[] a = fa.apply(SPECIES.length() * BUFFER_REPS, SPECIES.length());
5077         int[] b = fb.apply(SPECIES.length() * BUFFER_REPS, SPECIES.length());
5078 
5079         for (int i = 0; i < a.length; i += SPECIES.length()) {
5080             var av = VectorShuffle.fromArray(SPECIES, a, i);
5081             var bv = VectorShuffle.fromArray(SPECIES, b, i);
5082             boolean eq = av.equals(bv);
5083             int to = i + SPECIES.length();
5084             Assert.assertEquals(eq, Arrays.equals(a, i, to, b, i, to));
5085         }
5086     }
5087 
5088     @Test(dataProvider = "maskCompareOpProvider")
5089     static void maskEqualsDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa, IntFunction<boolean[]> fb) {
5090         boolean[] a = fa.apply(SPECIES.length());
5091         boolean[] b = fb.apply(SPECIES.length());
5092 
5093         for (int i = 0; i < a.length; i += SPECIES.length()) {
5094             var av = SPECIES.loadMask(a, i);
5095             var bv = SPECIES.loadMask(b, i);
5096             boolean equals = av.equals(bv);
5097             int to = i + SPECIES.length();
5098             Assert.assertEquals(equals, Arrays.equals(a, i, to, b, i, to));
5099         }
5100     }
5101 
5102     static boolean band(boolean a, boolean b) {
5103         return a & b;
5104     }
5105 
5106     @Test(dataProvider = "maskCompareOpProvider")
5107     static void maskAndDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa, IntFunction<boolean[]> fb) {
5108         boolean[] a = fa.apply(SPECIES.length());
5109         boolean[] b = fb.apply(SPECIES.length());
5110         boolean[] r = new boolean[a.length];
5111 
5112         for (int i = 0; i < a.length; i += SPECIES.length()) {
5113             var av = SPECIES.loadMask(a, i);
5114             var bv = SPECIES.loadMask(b, i);
5115             var cv = av.and(bv);
5116             cv.intoArray(r, i);
5117         }
5118         assertArraysEquals(r, a, b, Double64VectorTests::band);
5119     }
5120 
5121     static boolean bor(boolean a, boolean b) {
5122         return a | b;
5123     }
5124 
5125     @Test(dataProvider = "maskCompareOpProvider")
5126     static void maskOrDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa, IntFunction<boolean[]> fb) {
5127         boolean[] a = fa.apply(SPECIES.length());
5128         boolean[] b = fb.apply(SPECIES.length());
5129         boolean[] r = new boolean[a.length];
5130 
5131         for (int i = 0; i < a.length; i += SPECIES.length()) {
5132             var av = SPECIES.loadMask(a, i);
5133             var bv = SPECIES.loadMask(b, i);
5134             var cv = av.or(bv);
5135             cv.intoArray(r, i);
5136         }
5137         assertArraysEquals(r, a, b, Double64VectorTests::bor);
5138     }
5139 
5140     static boolean bxor(boolean a, boolean b) {
5141         return a != b;
5142     }
5143 
5144     @Test(dataProvider = "maskCompareOpProvider")
5145     static void maskXorDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa, IntFunction<boolean[]> fb) {
5146         boolean[] a = fa.apply(SPECIES.length());
5147         boolean[] b = fb.apply(SPECIES.length());
5148         boolean[] r = new boolean[a.length];
5149 
5150         for (int i = 0; i < a.length; i += SPECIES.length()) {
5151             var av = SPECIES.loadMask(a, i);
5152             var bv = SPECIES.loadMask(b, i);
5153             var cv = av.xor(bv);
5154             cv.intoArray(r, i);
5155         }
5156         assertArraysEquals(r, a, b, Double64VectorTests::bxor);
5157     }
5158 
5159     static boolean bandNot(boolean a, boolean b) {
5160         return a & !b;
5161     }
5162 
5163     @Test(dataProvider = "maskCompareOpProvider")
5164     static void maskAndNotDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa, IntFunction<boolean[]> fb) {
5165         boolean[] a = fa.apply(SPECIES.length());
5166         boolean[] b = fb.apply(SPECIES.length());
5167         boolean[] r = new boolean[a.length];
5168 
5169         for (int i = 0; i < a.length; i += SPECIES.length()) {
5170             var av = SPECIES.loadMask(a, i);
5171             var bv = SPECIES.loadMask(b, i);
5172             var cv = av.andNot(bv);
5173             cv.intoArray(r, i);
5174         }
5175         assertArraysEquals(r, a, b, Double64VectorTests::bandNot);
5176     }
5177 
5178     static boolean beq(boolean a, boolean b) {
5179         return (a == b);
5180     }
5181 
5182     @Test(dataProvider = "maskCompareOpProvider")
5183     static void maskEqDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa, IntFunction<boolean[]> fb) {
5184         boolean[] a = fa.apply(SPECIES.length());
5185         boolean[] b = fb.apply(SPECIES.length());
5186         boolean[] r = new boolean[a.length];
5187 
5188         for (int i = 0; i < a.length; i += SPECIES.length()) {
5189             var av = SPECIES.loadMask(a, i);
5190             var bv = SPECIES.loadMask(b, i);
5191             var cv = av.eq(bv);
5192             cv.intoArray(r, i);
5193         }
5194         assertArraysEquals(r, a, b, Double64VectorTests::beq);
5195     }
5196 
5197     @Test(dataProvider = "maskProvider")
5198     static void maskHashCodeDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa) {
5199         boolean[] a = fa.apply(SPECIES.length());
5200 
5201         for (int i = 0; i < a.length; i += SPECIES.length()) {
5202             var vmask = SPECIES.loadMask(a, i);
5203             int hash = vmask.hashCode();
5204 
5205             boolean subarr[] = Arrays.copyOfRange(a, i, i + SPECIES.length());
5206             int expectedHash = Objects.hash(SPECIES, Arrays.hashCode(subarr));
5207             Assert.assertTrue(hash == expectedHash, "at index " + i + ", hash should be = " + expectedHash + ", but is = " + hash);
5208         }
5209     }
5210 
5211     static int maskTrueCount(boolean[] a, int idx) {
5212         int trueCount = 0;
5213         for (int i = idx; i < idx + SPECIES.length(); i++) {
5214             trueCount += a[i] ? 1 : 0;
5215         }
5216         return trueCount;
5217     }
5218 
5219     @Test(dataProvider = "maskProvider")
5220     static void maskTrueCountDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa) {
5221         boolean[] a = fa.apply(SPECIES.length());
5222         int[] r = new int[a.length];
5223 
5224         for (int ic = 0; ic < INVOC_COUNT * INVOC_COUNT; ic++) {
5225             for (int i = 0; i < a.length; i += SPECIES.length()) {
5226                 var vmask = SPECIES.loadMask(a, i);
5227                 r[i] = vmask.trueCount();
5228             }
5229         }
5230 
5231         assertMaskReductionArraysEquals(r, a, Double64VectorTests::maskTrueCount);
5232     }
5233 
5234     static int maskLastTrue(boolean[] a, int idx) {
5235         int i = idx + SPECIES.length() - 1;
5236         for (; i >= idx; i--) {
5237             if (a[i]) {
5238                 break;
5239             }
5240         }
5241         return i - idx;
5242     }
5243 
5244     @Test(dataProvider = "maskProvider")
5245     static void maskLastTrueDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa) {
5246         boolean[] a = fa.apply(SPECIES.length());
5247         int[] r = new int[a.length];
5248 
5249         for (int ic = 0; ic < INVOC_COUNT * INVOC_COUNT; ic++) {
5250             for (int i = 0; i < a.length; i += SPECIES.length()) {
5251                 var vmask = SPECIES.loadMask(a, i);
5252                 r[i] = vmask.lastTrue();
5253             }
5254         }
5255 
5256         assertMaskReductionArraysEquals(r, a, Double64VectorTests::maskLastTrue);
5257     }
5258 
5259     static int maskFirstTrue(boolean[] a, int idx) {
5260         int i = idx;
5261         for (; i < idx + SPECIES.length(); i++) {
5262             if (a[i]) {
5263                 break;
5264             }
5265         }
5266         return i - idx;
5267     }
5268 
5269     @Test(dataProvider = "maskProvider")
5270     static void maskFirstTrueDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa) {
5271         boolean[] a = fa.apply(SPECIES.length());
5272         int[] r = new int[a.length];
5273 
5274         for (int ic = 0; ic < INVOC_COUNT * INVOC_COUNT; ic++) {
5275             for (int i = 0; i < a.length; i += SPECIES.length()) {
5276                 var vmask = SPECIES.loadMask(a, i);
5277                 r[i] = vmask.firstTrue();
5278             }
5279         }
5280 
5281         assertMaskReductionArraysEquals(r, a, Double64VectorTests::maskFirstTrue);
5282     }
5283 
5284     @Test(dataProvider = "maskProvider")
5285     static void maskCompressDouble64VectorTestsSmokeTest(IntFunction<boolean[]> fa) {
5286         int trueCount = 0;
5287         boolean[] a = fa.apply(SPECIES.length());
5288 
5289         for (int ic = 0; ic < INVOC_COUNT * INVOC_COUNT; ic++) {
5290             for (int i = 0; i < a.length; i += SPECIES.length()) {
5291                 var vmask = SPECIES.loadMask(a, i);
5292                 trueCount = vmask.trueCount();
5293                 var rmask = vmask.compress();
5294                 for (int j = 0; j < SPECIES.length(); j++)  {
5295                     Assert.assertEquals(rmask.laneIsSet(j), j < trueCount);
5296                 }
5297             }
5298         }
5299     }
5300 
5301     @DataProvider
5302     public static Object[][] longMaskProvider() {
5303         return new Object[][]{
5304                 {0xFFFFFFFFFFFFFFFFL},
5305                 {0x0000000000000000L},
5306                 {0x5555555555555555L},
5307                 {0x0123456789abcdefL},
5308         };
5309     }
5310 
5311     @Test(dataProvider = "longMaskProvider")
5312     static void maskFromToLongDouble64VectorTestsSmokeTest(long inputLong) {
5313         var vmask = VectorMask.fromLong(SPECIES, inputLong);
5314         long outputLong = vmask.toLong();
5315         Assert.assertEquals(outputLong, (inputLong & (((0xFFFFFFFFFFFFFFFFL >>> (64 - SPECIES.length()))))));
5316     }
5317 
5318     @DataProvider
5319     public static Object[][] offsetProvider() {
5320         return new Object[][]{
5321                 {0},
5322                 {-1},
5323                 {+1},
5324                 {+2},
5325                 {-2},
5326         };
5327     }
5328 
5329     @Test(dataProvider = "offsetProvider")
5330     static void indexInRangeDouble64VectorTestsSmokeTest(int offset) {
5331         int limit = SPECIES.length() * BUFFER_REPS;
5332         for (int i = 0; i < limit; i += SPECIES.length()) {
5333             var actualMask = SPECIES.indexInRange(i + offset, limit);
5334             var expectedMask = SPECIES.maskAll(true).indexInRange(i + offset, limit);
5335             assert(actualMask.equals(expectedMask));
5336             for (int j = 0; j < SPECIES.length(); j++)  {
5337                 int index = i + j + offset;
5338                 Assert.assertEquals(actualMask.laneIsSet(j), index >= 0 && index < limit);
5339             }
5340         }
5341     }
5342 
5343     @Test(dataProvider = "offsetProvider")
5344     static void indexInRangeLongDouble64VectorTestsSmokeTest(int offset) {
5345         long limit = SPECIES.length() * BUFFER_REPS;
5346         for (long i = 0; i < limit; i += SPECIES.length()) {
5347             var actualMask = SPECIES.indexInRange(i + offset, limit);
5348             var expectedMask = SPECIES.maskAll(true).indexInRange(i + offset, limit);
5349             assert(actualMask.equals(expectedMask));
5350             for (int j = 0; j < SPECIES.length(); j++)  {
5351                 long index = i + j + offset;
5352                 Assert.assertEquals(actualMask.laneIsSet(j), index >= 0 && index < limit);
5353             }
5354         }
5355     }
5356 
5357     @DataProvider
5358     public static Object[][] lengthProvider() {
5359         return new Object[][]{
5360                 {0},
5361                 {1},
5362                 {32},
5363                 {37},
5364                 {1024},
5365                 {1024+1},
5366                 {1024+5},
5367         };
5368     }
5369 
5370     @Test(dataProvider = "lengthProvider")
5371     static void loopBoundDouble64VectorTestsSmokeTest(int length) {
5372         int actualLoopBound = SPECIES.loopBound(length);
5373         int expectedLoopBound = length - Math.floorMod(length, SPECIES.length());
5374         Assert.assertEquals(actualLoopBound, expectedLoopBound);
5375     }
5376 
5377     @Test(dataProvider = "lengthProvider")
5378     static void loopBoundLongDouble64VectorTestsSmokeTest(int _length) {
5379         long length = _length;
5380         long actualLoopBound = SPECIES.loopBound(length);
5381         long expectedLoopBound = length - Math.floorMod(length, SPECIES.length());
5382         Assert.assertEquals(actualLoopBound, expectedLoopBound);
5383     }
5384 
5385     @Test
5386     static void ElementSizeDouble64VectorTestsSmokeTest() {
5387         DoubleVector av = DoubleVector.zero(SPECIES);
5388         int elsize = av.elementSize();
5389         Assert.assertEquals(elsize, Double.SIZE);
5390     }
5391 
5392     @Test
5393     static void VectorShapeDouble64VectorTestsSmokeTest() {
5394         DoubleVector av = DoubleVector.zero(SPECIES);
5395         VectorShape vsh = av.shape();
5396         assert(vsh.equals(VectorShape.S_64_BIT));
5397     }
5398 
5399     @Test
5400     static void ShapeWithLanesDouble64VectorTestsSmokeTest() {
5401         DoubleVector av = DoubleVector.zero(SPECIES);
5402         VectorShape vsh = av.shape();
5403         VectorSpecies species = vsh.withLanes(double.class);
5404         assert(species.equals(SPECIES));
5405     }
5406 
5407     @Test
5408     static void ElementTypeDouble64VectorTestsSmokeTest() {
5409         DoubleVector av = DoubleVector.zero(SPECIES);
5410         assert(av.species().elementType() == double.class);
5411     }
5412 
5413     @Test
5414     static void SpeciesElementSizeDouble64VectorTestsSmokeTest() {
5415         DoubleVector av = DoubleVector.zero(SPECIES);
5416         assert(av.species().elementSize() == Double.SIZE);
5417     }
5418 
5419     @Test
5420     static void VectorTypeDouble64VectorTestsSmokeTest() {
5421         DoubleVector av = DoubleVector.zero(SPECIES);
5422         assert(av.species().vectorType() == av.getClass());
5423     }
5424 
5425     @Test
5426     static void WithLanesDouble64VectorTestsSmokeTest() {
5427         DoubleVector av = DoubleVector.zero(SPECIES);
5428         VectorSpecies species = av.species().withLanes(double.class);
5429         assert(species.equals(SPECIES));
5430     }
5431 
5432     @Test
5433     static void WithShapeDouble64VectorTestsSmokeTest() {
5434         DoubleVector av = DoubleVector.zero(SPECIES);
5435         VectorShape vsh = av.shape();
5436         VectorSpecies species = av.species().withShape(vsh);
5437         assert(species.equals(SPECIES));
5438     }
5439 
5440     @Test
5441     static void MaskAllTrueDouble64VectorTestsSmokeTest() {
5442         for (int ic = 0; ic < INVOC_COUNT; ic++) {
5443           Assert.assertEquals(SPECIES.maskAll(true).toLong(), -1L >>> (64 - SPECIES.length()));
5444         }
5445     }
5446 }