1/* 2 * Copyright (c) 2015, 2016, 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 * @bug 8154556 27 * @run testng/othervm -Diters=20000 -XX:TieredStopAtLevel=1 VarHandleTestByteArrayAsFloat 28 * @run testng/othervm -Diters=20000 VarHandleTestByteArrayAsFloat 29 * @run testng/othervm -Diters=20000 -XX:-TieredCompilation VarHandleTestByteArrayAsFloat 30 */ 31 32import org.testng.annotations.DataProvider; 33import org.testng.annotations.Test; 34 35import java.lang.invoke.MethodHandles; 36import java.lang.invoke.VarHandle; 37import java.nio.ByteBuffer; 38import java.nio.ByteOrder; 39import java.util.ArrayList; 40import java.util.Arrays; 41import java.util.EnumSet; 42import java.util.List; 43 44import static org.testng.Assert.*; 45 46public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { 47 static final int SIZE = Float.BYTES; 48 49 static final float VALUE_1 = 0x01020304; 50 51 static final float VALUE_2 = 0x11121314; 52 53 static final float VALUE_3 = 0xFFFEFDFC; 54 55 56 @Override 57 public void setupVarHandleSources() { 58 // Combinations of VarHandle byte[] or ByteBuffer 59 vhss = new ArrayList<>(); 60 for (MemoryMode endianess : Arrays.asList(MemoryMode.BIG_ENDIAN, MemoryMode.LITTLE_ENDIAN)) { 61 62 ByteOrder bo = endianess == MemoryMode.BIG_ENDIAN 63 ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN; 64 VarHandleSource aeh = new VarHandleSource( 65 MethodHandles.byteArrayViewVarHandle(float[].class, bo), 66 endianess, MemoryMode.READ_WRITE); 67 vhss.add(aeh); 68 69 VarHandleSource bbh = new VarHandleSource( 70 MethodHandles.byteBufferViewVarHandle(float[].class, bo), 71 endianess, MemoryMode.READ_WRITE); 72 vhss.add(bbh); 73 } 74 } 75 76 77 @Test(dataProvider = "varHandlesProvider") 78 public void testIsAccessModeSupported(VarHandleSource vhs) { 79 VarHandle vh = vhs.s; 80 81 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET)); 82 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET)); 83 84 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); 85 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); 86 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); 87 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); 88 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); 89 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); 90 91 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); 92 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); 93 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); 94 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); 95 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); 96 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); 97 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); 98 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); 99 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); 100 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); 101 assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); 102 103 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); 104 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); 105 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); 106 107 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); 108 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); 109 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); 110 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); 111 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); 112 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); 113 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); 114 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); 115 assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); 116 } 117 118 @Test(dataProvider = "typesProvider") 119 public void testTypes(VarHandle vh, List<java.lang.Class<?>> pts) { 120 assertEquals(vh.varType(), float.class); 121 122 assertEquals(vh.coordinateTypes(), pts); 123 124 testTypes(vh); 125 } 126 127 128 @DataProvider 129 public Object[][] accessTestCaseProvider() throws Exception { 130 List<AccessTestCase<?>> cases = new ArrayList<>(); 131 132 for (ByteArrayViewSource<?> bav : bavss) { 133 for (VarHandleSource vh : vhss) { 134 if (vh.matches(bav)) { 135 if (bav instanceof ByteArraySource) { 136 ByteArraySource bas = (ByteArraySource) bav; 137 138 cases.add(new VarHandleSourceAccessTestCase( 139 "read write", bav, vh, h -> testArrayReadWrite(bas, h), 140 true)); 141 cases.add(new VarHandleSourceAccessTestCase( 142 "unsupported", bav, vh, h -> testArrayUnsupported(bas, h), 143 false)); 144 cases.add(new VarHandleSourceAccessTestCase( 145 "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bas, h), 146 false)); 147 cases.add(new VarHandleSourceAccessTestCase( 148 "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bas, h), 149 false)); 150 } 151 else { 152 ByteBufferSource bbs = (ByteBufferSource) bav; 153 154 if (MemoryMode.READ_WRITE.isSet(bav.memoryModes)) { 155 cases.add(new VarHandleSourceAccessTestCase( 156 "read write", bav, vh, h -> testArrayReadWrite(bbs, h), 157 true)); 158 } 159 else { 160 cases.add(new VarHandleSourceAccessTestCase( 161 "read only", bav, vh, h -> testArrayReadOnly(bbs, h), 162 true)); 163 } 164 165 cases.add(new VarHandleSourceAccessTestCase( 166 "unsupported", bav, vh, h -> testArrayUnsupported(bbs, h), 167 false)); 168 cases.add(new VarHandleSourceAccessTestCase( 169 "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bbs, h), 170 false)); 171 cases.add(new VarHandleSourceAccessTestCase( 172 "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), 173 false)); 174 } 175 } 176 } 177 } 178 179 // Work around issue with jtreg summary reporting which truncates 180 // the String result of Object.toString to 30 characters, hence 181 // the first dummy argument 182 return cases.stream().map(tc -> new Object[]{tc.toString(), tc}).toArray(Object[][]::new); 183 } 184 185 @Test(dataProvider = "accessTestCaseProvider") 186 public <T> void testAccess(String desc, AccessTestCase<T> atc) throws Throwable { 187 T t = atc.get(); 188 int iters = atc.requiresLoop() ? ITERS : 1; 189 for (int c = 0; c < iters; c++) { 190 atc.testAccess(t); 191 } 192 } 193 194 195 static void testArrayUnsupported(ByteArraySource bs, VarHandleSource vhs) { 196 VarHandle vh = vhs.s; 197 byte[] array = bs.s; 198 int ci = 1; 199 200 201 checkUOE(() -> { 202 float o = (float) vh.getAndAdd(array, ci, VALUE_1); 203 }); 204 205 checkUOE(() -> { 206 float o = (float) vh.getAndAddAcquire(array, ci, VALUE_1); 207 }); 208 209 checkUOE(() -> { 210 float o = (float) vh.getAndAddRelease(array, ci, VALUE_1); 211 }); 212 213 checkUOE(() -> { 214 float o = (float) vh.getAndBitwiseOr(array, ci, VALUE_1); 215 }); 216 217 checkUOE(() -> { 218 float o = (float) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); 219 }); 220 221 checkUOE(() -> { 222 float o = (float) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); 223 }); 224 225 checkUOE(() -> { 226 float o = (float) vh.getAndBitwiseAnd(array, ci, VALUE_1); 227 }); 228 229 checkUOE(() -> { 230 float o = (float) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); 231 }); 232 233 checkUOE(() -> { 234 float o = (float) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); 235 }); 236 237 checkUOE(() -> { 238 float o = (float) vh.getAndBitwiseXor(array, ci, VALUE_1); 239 }); 240 241 checkUOE(() -> { 242 float o = (float) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); 243 }); 244 245 checkUOE(() -> { 246 float o = (float) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); 247 }); 248 } 249 250 static void testArrayUnsupported(ByteBufferSource bs, VarHandleSource vhs) { 251 VarHandle vh = vhs.s; 252 ByteBuffer array = bs.s; 253 int ci = 0; 254 boolean readOnly = MemoryMode.READ_ONLY.isSet(bs.memoryModes); 255 256 if (readOnly) { 257 checkROBE(() -> { 258 vh.set(array, ci, VALUE_1); 259 }); 260 } 261 262 if (readOnly) { 263 checkROBE(() -> { 264 vh.setVolatile(array, ci, VALUE_1); 265 }); 266 267 checkROBE(() -> { 268 vh.setRelease(array, ci, VALUE_1); 269 }); 270 271 checkROBE(() -> { 272 vh.setOpaque(array, ci, VALUE_1); 273 }); 274 275 checkROBE(() -> { 276 boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); 277 }); 278 279 checkROBE(() -> { 280 float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); 281 }); 282 283 checkROBE(() -> { 284 float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); 285 }); 286 287 checkROBE(() -> { 288 float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); 289 }); 290 291 checkROBE(() -> { 292 boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); 293 }); 294 295 checkROBE(() -> { 296 boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); 297 }); 298 299 checkROBE(() -> { 300 boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); 301 }); 302 303 checkROBE(() -> { 304 boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); 305 }); 306 307 checkROBE(() -> { 308 float o = (float) vh.getAndSet(array, ci, VALUE_1); 309 }); 310 311 checkROBE(() -> { 312 float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); 313 }); 314 315 checkROBE(() -> { 316 float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); 317 }); 318 319 320 checkUOE(() -> { 321 float o = (float) vh.getAndAdd(array, ci, VALUE_1); 322 }); 323 324 checkUOE(() -> { 325 float o = (float) vh.getAndAddAcquire(array, ci, VALUE_1); 326 }); 327 328 checkUOE(() -> { 329 float o = (float) vh.getAndAddRelease(array, ci, VALUE_1); 330 }); 331 332 checkUOE(() -> { 333 float o = (float) vh.getAndBitwiseOr(array, ci, VALUE_1); 334 }); 335 336 checkUOE(() -> { 337 float o = (float) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); 338 }); 339 340 checkUOE(() -> { 341 float o = (float) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); 342 }); 343 344 checkUOE(() -> { 345 float o = (float) vh.getAndBitwiseAnd(array, ci, VALUE_1); 346 }); 347 348 checkUOE(() -> { 349 float o = (float) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); 350 }); 351 352 checkUOE(() -> { 353 float o = (float) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); 354 }); 355 356 checkUOE(() -> { 357 float o = (float) vh.getAndBitwiseXor(array, ci, VALUE_1); 358 }); 359 360 checkUOE(() -> { 361 float o = (float) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); 362 }); 363 364 checkUOE(() -> { 365 float o = (float) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); 366 }); 367 } 368 else { 369 checkUOE(() -> { 370 float o = (float) vh.getAndAdd(array, ci, VALUE_1); 371 }); 372 373 checkUOE(() -> { 374 float o = (float) vh.getAndAddAcquire(array, ci, VALUE_1); 375 }); 376 377 checkUOE(() -> { 378 float o = (float) vh.getAndAddRelease(array, ci, VALUE_1); 379 }); 380 checkUOE(() -> { 381 float o = (float) vh.getAndBitwiseOr(array, ci, VALUE_1); 382 }); 383 384 checkUOE(() -> { 385 float o = (float) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); 386 }); 387 388 checkUOE(() -> { 389 float o = (float) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); 390 }); 391 392 checkUOE(() -> { 393 float o = (float) vh.getAndBitwiseAnd(array, ci, VALUE_1); 394 }); 395 396 checkUOE(() -> { 397 float o = (float) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); 398 }); 399 400 checkUOE(() -> { 401 float o = (float) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); 402 }); 403 404 checkUOE(() -> { 405 float o = (float) vh.getAndBitwiseXor(array, ci, VALUE_1); 406 }); 407 408 checkUOE(() -> { 409 float o = (float) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); 410 }); 411 412 checkUOE(() -> { 413 float o = (float) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); 414 }); 415 } 416 } 417 418 419 static void testArrayIndexOutOfBounds(ByteArraySource bs, VarHandleSource vhs) throws Throwable { 420 VarHandle vh = vhs.s; 421 byte[] array = bs.s; 422 423 int length = array.length - SIZE + 1; 424 for (int i : new int[]{-1, Integer.MIN_VALUE, length, length + 1, Integer.MAX_VALUE}) { 425 final int ci = i; 426 427 checkIOOBE(() -> { 428 float x = (float) vh.get(array, ci); 429 }); 430 431 checkIOOBE(() -> { 432 vh.set(array, ci, VALUE_1); 433 }); 434 435 checkIOOBE(() -> { 436 float x = (float) vh.getVolatile(array, ci); 437 }); 438 439 checkIOOBE(() -> { 440 float x = (float) vh.getAcquire(array, ci); 441 }); 442 443 checkIOOBE(() -> { 444 float x = (float) vh.getOpaque(array, ci); 445 }); 446 447 checkIOOBE(() -> { 448 vh.setVolatile(array, ci, VALUE_1); 449 }); 450 451 checkIOOBE(() -> { 452 vh.setRelease(array, ci, VALUE_1); 453 }); 454 455 checkIOOBE(() -> { 456 vh.setOpaque(array, ci, VALUE_1); 457 }); 458 459 checkIOOBE(() -> { 460 boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); 461 }); 462 463 checkIOOBE(() -> { 464 float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); 465 }); 466 467 checkIOOBE(() -> { 468 float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); 469 }); 470 471 checkIOOBE(() -> { 472 float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); 473 }); 474 475 checkIOOBE(() -> { 476 boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); 477 }); 478 479 checkIOOBE(() -> { 480 boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); 481 }); 482 483 checkIOOBE(() -> { 484 boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); 485 }); 486 487 checkIOOBE(() -> { 488 boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); 489 }); 490 491 checkIOOBE(() -> { 492 float o = (float) vh.getAndSet(array, ci, VALUE_1); 493 }); 494 495 checkIOOBE(() -> { 496 float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); 497 }); 498 499 checkIOOBE(() -> { 500 float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); 501 }); 502 503 504 505 } 506 } 507 508 static void testArrayIndexOutOfBounds(ByteBufferSource bs, VarHandleSource vhs) throws Throwable { 509 VarHandle vh = vhs.s; 510 ByteBuffer array = bs.s; 511 512 boolean readOnly = MemoryMode.READ_ONLY.isSet(bs.memoryModes); 513 514 int length = array.limit() - SIZE + 1; 515 for (int i : new int[]{-1, Integer.MIN_VALUE, length, length + 1, Integer.MAX_VALUE}) { 516 final int ci = i; 517 518 checkIOOBE(() -> { 519 float x = (float) vh.get(array, ci); 520 }); 521 522 if (!readOnly) { 523 checkIOOBE(() -> { 524 vh.set(array, ci, VALUE_1); 525 }); 526 } 527 528 checkIOOBE(() -> { 529 float x = (float) vh.getVolatile(array, ci); 530 }); 531 532 checkIOOBE(() -> { 533 float x = (float) vh.getAcquire(array, ci); 534 }); 535 536 checkIOOBE(() -> { 537 float x = (float) vh.getOpaque(array, ci); 538 }); 539 540 if (!readOnly) { 541 checkIOOBE(() -> { 542 vh.setVolatile(array, ci, VALUE_1); 543 }); 544 545 checkIOOBE(() -> { 546 vh.setRelease(array, ci, VALUE_1); 547 }); 548 549 checkIOOBE(() -> { 550 vh.setOpaque(array, ci, VALUE_1); 551 }); 552 553 checkIOOBE(() -> { 554 boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); 555 }); 556 557 checkIOOBE(() -> { 558 float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); 559 }); 560 561 checkIOOBE(() -> { 562 float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); 563 }); 564 565 checkIOOBE(() -> { 566 float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); 567 }); 568 569 checkIOOBE(() -> { 570 boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); 571 }); 572 573 checkIOOBE(() -> { 574 boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); 575 }); 576 577 checkIOOBE(() -> { 578 boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); 579 }); 580 581 checkIOOBE(() -> { 582 boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); 583 }); 584 585 checkIOOBE(() -> { 586 float o = (float) vh.getAndSet(array, ci, VALUE_1); 587 }); 588 589 checkIOOBE(() -> { 590 float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); 591 }); 592 593 checkIOOBE(() -> { 594 float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); 595 }); 596 597 598 } 599 } 600 } 601 602 static void testArrayMisalignedAccess(ByteArraySource bs, VarHandleSource vhs) throws Throwable { 603 VarHandle vh = vhs.s; 604 byte[] array = bs.s; 605 606 int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); 607 608 int length = array.length - SIZE + 1; 609 for (int i = 0; i < length; i++) { 610 boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; 611 final int ci = i; 612 613 if (!iAligned) { 614 checkISE(() -> { 615 float x = (float) vh.getVolatile(array, ci); 616 }); 617 618 checkISE(() -> { 619 float x = (float) vh.getAcquire(array, ci); 620 }); 621 622 checkISE(() -> { 623 float x = (float) vh.getOpaque(array, ci); 624 }); 625 626 checkISE(() -> { 627 vh.setVolatile(array, ci, VALUE_1); 628 }); 629 630 checkISE(() -> { 631 vh.setRelease(array, ci, VALUE_1); 632 }); 633 634 checkISE(() -> { 635 vh.setOpaque(array, ci, VALUE_1); 636 }); 637 638 checkISE(() -> { 639 boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); 640 }); 641 642 checkISE(() -> { 643 float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); 644 }); 645 646 checkISE(() -> { 647 float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); 648 }); 649 650 checkISE(() -> { 651 float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); 652 }); 653 654 checkISE(() -> { 655 boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); 656 }); 657 658 checkISE(() -> { 659 boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); 660 }); 661 662 checkISE(() -> { 663 boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); 664 }); 665 666 checkISE(() -> { 667 boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); 668 }); 669 670 checkISE(() -> { 671 float o = (float) vh.getAndSet(array, ci, VALUE_1); 672 }); 673 674 checkISE(() -> { 675 float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); 676 }); 677 678 checkISE(() -> { 679 float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); 680 }); 681 682 683 } 684 } 685 } 686 687 static void testArrayMisalignedAccess(ByteBufferSource bs, VarHandleSource vhs) throws Throwable { 688 VarHandle vh = vhs.s; 689 ByteBuffer array = bs.s; 690 691 boolean readOnly = MemoryMode.READ_ONLY.isSet(bs.memoryModes); 692 int misalignmentAtZero = array.alignmentOffset(0, SIZE); 693 694 int length = array.limit() - SIZE + 1; 695 for (int i = 0; i < length; i++) { 696 boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; 697 final int ci = i; 698 699 if (!iAligned) { 700 checkISE(() -> { 701 float x = (float) vh.getVolatile(array, ci); 702 }); 703 704 checkISE(() -> { 705 float x = (float) vh.getAcquire(array, ci); 706 }); 707 708 checkISE(() -> { 709 float x = (float) vh.getOpaque(array, ci); 710 }); 711 712 if (!readOnly) { 713 checkISE(() -> { 714 vh.setVolatile(array, ci, VALUE_1); 715 }); 716 717 checkISE(() -> { 718 vh.setRelease(array, ci, VALUE_1); 719 }); 720 721 checkISE(() -> { 722 vh.setOpaque(array, ci, VALUE_1); 723 }); 724 725 checkISE(() -> { 726 boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); 727 }); 728 729 checkISE(() -> { 730 float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); 731 }); 732 733 checkISE(() -> { 734 float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); 735 }); 736 737 checkISE(() -> { 738 float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); 739 }); 740 741 checkISE(() -> { 742 boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); 743 }); 744 745 checkISE(() -> { 746 boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); 747 }); 748 749 checkISE(() -> { 750 boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); 751 }); 752 753 checkISE(() -> { 754 boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); 755 }); 756 757 checkISE(() -> { 758 float o = (float) vh.getAndSet(array, ci, VALUE_1); 759 }); 760 761 checkISE(() -> { 762 float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); 763 }); 764 765 checkISE(() -> { 766 float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); 767 }); 768 769 770 } 771 } 772 } 773 } 774 775 static void testArrayReadWrite(ByteArraySource bs, VarHandleSource vhs) { 776 VarHandle vh = vhs.s; 777 byte[] array = bs.s; 778 779 int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); 780 781 bs.fill((byte) 0xff); 782 int length = array.length - SIZE + 1; 783 for (int i = 0; i < length; i++) { 784 boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; 785 786 // Plain 787 { 788 vh.set(array, i, VALUE_1); 789 float x = (float) vh.get(array, i); 790 assertEquals(x, VALUE_1, "get float value"); 791 } 792 793 794 if (iAligned) { 795 // Volatile 796 { 797 vh.setVolatile(array, i, VALUE_2); 798 float x = (float) vh.getVolatile(array, i); 799 assertEquals(x, VALUE_2, "setVolatile float value"); 800 } 801 802 // Lazy 803 { 804 vh.setRelease(array, i, VALUE_1); 805 float x = (float) vh.getAcquire(array, i); 806 assertEquals(x, VALUE_1, "setRelease float value"); 807 } 808 809 // Opaque 810 { 811 vh.setOpaque(array, i, VALUE_2); 812 float x = (float) vh.getOpaque(array, i); 813 assertEquals(x, VALUE_2, "setOpaque float value"); 814 } 815 816 vh.set(array, i, VALUE_1); 817 818 // Compare 819 { 820 boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_2); 821 assertEquals(r, true, "success compareAndSet float"); 822 float x = (float) vh.get(array, i); 823 assertEquals(x, VALUE_2, "success compareAndSet float value"); 824 } 825 826 { 827 boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_3); 828 assertEquals(r, false, "failing compareAndSet float"); 829 float x = (float) vh.get(array, i); 830 assertEquals(x, VALUE_2, "failing compareAndSet float value"); 831 } 832 833 { 834 float r = (float) vh.compareAndExchange(array, i, VALUE_2, VALUE_1); 835 assertEquals(r, VALUE_2, "success compareAndExchange float"); 836 float x = (float) vh.get(array, i); 837 assertEquals(x, VALUE_1, "success compareAndExchange float value"); 838 } 839 840 { 841 float r = (float) vh.compareAndExchange(array, i, VALUE_2, VALUE_3); 842 assertEquals(r, VALUE_1, "failing compareAndExchange float"); 843 float x = (float) vh.get(array, i); 844 assertEquals(x, VALUE_1, "failing compareAndExchange float value"); 845 } 846 847 { 848 float r = (float) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_2); 849 assertEquals(r, VALUE_1, "success compareAndExchangeAcquire float"); 850 float x = (float) vh.get(array, i); 851 assertEquals(x, VALUE_2, "success compareAndExchangeAcquire float value"); 852 } 853 854 { 855 float r = (float) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_3); 856 assertEquals(r, VALUE_2, "failing compareAndExchangeAcquire float"); 857 float x = (float) vh.get(array, i); 858 assertEquals(x, VALUE_2, "failing compareAndExchangeAcquire float value"); 859 } 860 861 { 862 float r = (float) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_1); 863 assertEquals(r, VALUE_2, "success compareAndExchangeRelease float"); 864 float x = (float) vh.get(array, i); 865 assertEquals(x, VALUE_1, "success compareAndExchangeRelease float value"); 866 } 867 868 { 869 float r = (float) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_3); 870 assertEquals(r, VALUE_1, "failing compareAndExchangeRelease float"); 871 float x = (float) vh.get(array, i); 872 assertEquals(x, VALUE_1, "failing compareAndExchangeRelease float value"); 873 } 874 875 { 876 boolean success = false; 877 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { 878 success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_2); 879 } 880 assertEquals(success, true, "weakCompareAndSetPlain float"); 881 float x = (float) vh.get(array, i); 882 assertEquals(x, VALUE_2, "weakCompareAndSetPlain float value"); 883 } 884 885 { 886 boolean success = false; 887 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { 888 success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_1); 889 } 890 assertEquals(success, true, "weakCompareAndSetAcquire float"); 891 float x = (float) vh.get(array, i); 892 assertEquals(x, VALUE_1, "weakCompareAndSetAcquire float"); 893 } 894 895 { 896 boolean success = false; 897 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { 898 success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_2); 899 } 900 assertEquals(success, true, "weakCompareAndSetRelease float"); 901 float x = (float) vh.get(array, i); 902 assertEquals(x, VALUE_2, "weakCompareAndSetRelease float"); 903 } 904 905 { 906 boolean success = false; 907 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { 908 success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_1); 909 } 910 assertEquals(success, true, "weakCompareAndSet float"); 911 float x = (float) vh.get(array, i); 912 assertEquals(x, VALUE_1, "weakCompareAndSet float"); 913 } 914 915 // Compare set and get 916 { 917 vh.set(array, i, VALUE_1); 918 919 float o = (float) vh.getAndSet(array, i, VALUE_2); 920 assertEquals(o, VALUE_1, "getAndSet float"); 921 float x = (float) vh.get(array, i); 922 assertEquals(x, VALUE_2, "getAndSet float value"); 923 } 924 925 { 926 vh.set(array, i, VALUE_1); 927 928 float o = (float) vh.getAndSetAcquire(array, i, VALUE_2); 929 assertEquals(o, VALUE_1, "getAndSetAcquire float"); 930 float x = (float) vh.get(array, i); 931 assertEquals(x, VALUE_2, "getAndSetAcquire float value"); 932 } 933 934 { 935 vh.set(array, i, VALUE_1); 936 937 float o = (float) vh.getAndSetRelease(array, i, VALUE_2); 938 assertEquals(o, VALUE_1, "getAndSetRelease float"); 939 float x = (float) vh.get(array, i); 940 assertEquals(x, VALUE_2, "getAndSetRelease float value"); 941 } 942 943 944 } 945 } 946 } 947 948 949 static void testArrayReadWrite(ByteBufferSource bs, VarHandleSource vhs) { 950 VarHandle vh = vhs.s; 951 ByteBuffer array = bs.s; 952 953 int misalignmentAtZero = array.alignmentOffset(0, SIZE); 954 955 bs.fill((byte) 0xff); 956 int length = array.limit() - SIZE + 1; 957 for (int i = 0; i < length; i++) { 958 boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; 959 960 // Plain 961 { 962 vh.set(array, i, VALUE_1); 963 float x = (float) vh.get(array, i); 964 assertEquals(x, VALUE_1, "get float value"); 965 } 966 967 if (iAligned) { 968 // Volatile 969 { 970 vh.setVolatile(array, i, VALUE_2); 971 float x = (float) vh.getVolatile(array, i); 972 assertEquals(x, VALUE_2, "setVolatile float value"); 973 } 974 975 // Lazy 976 { 977 vh.setRelease(array, i, VALUE_1); 978 float x = (float) vh.getAcquire(array, i); 979 assertEquals(x, VALUE_1, "setRelease float value"); 980 } 981 982 // Opaque 983 { 984 vh.setOpaque(array, i, VALUE_2); 985 float x = (float) vh.getOpaque(array, i); 986 assertEquals(x, VALUE_2, "setOpaque float value"); 987 } 988 989 vh.set(array, i, VALUE_1); 990 991 // Compare 992 { 993 boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_2); 994 assertEquals(r, true, "success compareAndSet float"); 995 float x = (float) vh.get(array, i); 996 assertEquals(x, VALUE_2, "success compareAndSet float value"); 997 } 998 999 { 1000 boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_3); 1001 assertEquals(r, false, "failing compareAndSet float"); 1002 float x = (float) vh.get(array, i); 1003 assertEquals(x, VALUE_2, "failing compareAndSet float value"); 1004 } 1005 1006 { 1007 float r = (float) vh.compareAndExchange(array, i, VALUE_2, VALUE_1); 1008 assertEquals(r, VALUE_2, "success compareAndExchange float"); 1009 float x = (float) vh.get(array, i); 1010 assertEquals(x, VALUE_1, "success compareAndExchange float value"); 1011 } 1012 1013 { 1014 float r = (float) vh.compareAndExchange(array, i, VALUE_2, VALUE_3); 1015 assertEquals(r, VALUE_1, "failing compareAndExchange float"); 1016 float x = (float) vh.get(array, i); 1017 assertEquals(x, VALUE_1, "failing compareAndExchange float value"); 1018 } 1019 1020 { 1021 float r = (float) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_2); 1022 assertEquals(r, VALUE_1, "success compareAndExchangeAcquire float"); 1023 float x = (float) vh.get(array, i); 1024 assertEquals(x, VALUE_2, "success compareAndExchangeAcquire float value"); 1025 } 1026 1027 { 1028 float r = (float) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_3); 1029 assertEquals(r, VALUE_2, "failing compareAndExchangeAcquire float"); 1030 float x = (float) vh.get(array, i); 1031 assertEquals(x, VALUE_2, "failing compareAndExchangeAcquire float value"); 1032 } 1033 1034 { 1035 float r = (float) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_1); 1036 assertEquals(r, VALUE_2, "success compareAndExchangeRelease float"); 1037 float x = (float) vh.get(array, i); 1038 assertEquals(x, VALUE_1, "success compareAndExchangeRelease float value"); 1039 } 1040 1041 { 1042 float r = (float) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_3); 1043 assertEquals(r, VALUE_1, "failing compareAndExchangeRelease float"); 1044 float x = (float) vh.get(array, i); 1045 assertEquals(x, VALUE_1, "failing compareAndExchangeRelease float value"); 1046 } 1047 1048 { 1049 boolean success = false; 1050 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { 1051 success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_2); 1052 } 1053 assertEquals(success, true, "weakCompareAndSetPlain float"); 1054 float x = (float) vh.get(array, i); 1055 assertEquals(x, VALUE_2, "weakCompareAndSetPlain float value"); 1056 } 1057 1058 { 1059 boolean success = false; 1060 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { 1061 success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_1); 1062 } 1063 assertEquals(success, true, "weakCompareAndSetAcquire float"); 1064 float x = (float) vh.get(array, i); 1065 assertEquals(x, VALUE_1, "weakCompareAndSetAcquire float"); 1066 } 1067 1068 { 1069 boolean success = false; 1070 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { 1071 success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_2); 1072 } 1073 assertEquals(success, true, "weakCompareAndSetRelease float"); 1074 float x = (float) vh.get(array, i); 1075 assertEquals(x, VALUE_2, "weakCompareAndSetRelease float"); 1076 } 1077 1078 { 1079 boolean success = false; 1080 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { 1081 success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_1); 1082 } 1083 assertEquals(success, true, "weakCompareAndSet float"); 1084 float x = (float) vh.get(array, i); 1085 assertEquals(x, VALUE_1, "weakCompareAndSet float"); 1086 } 1087 1088 // Compare set and get 1089 { 1090 vh.set(array, i, VALUE_1); 1091 1092 float o = (float) vh.getAndSet(array, i, VALUE_2); 1093 assertEquals(o, VALUE_1, "getAndSet float"); 1094 float x = (float) vh.get(array, i); 1095 assertEquals(x, VALUE_2, "getAndSet float value"); 1096 } 1097 1098 { 1099 vh.set(array, i, VALUE_1); 1100 1101 float o = (float) vh.getAndSetAcquire(array, i, VALUE_2); 1102 assertEquals(o, VALUE_1, "getAndSetAcquire float"); 1103 float x = (float) vh.get(array, i); 1104 assertEquals(x, VALUE_2, "getAndSetAcquire float value"); 1105 } 1106 1107 { 1108 vh.set(array, i, VALUE_1); 1109 1110 float o = (float) vh.getAndSetRelease(array, i, VALUE_2); 1111 assertEquals(o, VALUE_1, "getAndSetRelease float"); 1112 float x = (float) vh.get(array, i); 1113 assertEquals(x, VALUE_2, "getAndSetRelease float value"); 1114 } 1115 1116 1117 } 1118 } 1119 } 1120 1121 static void testArrayReadOnly(ByteBufferSource bs, VarHandleSource vhs) { 1122 VarHandle vh = vhs.s; 1123 ByteBuffer array = bs.s; 1124 1125 int misalignmentAtZero = array.alignmentOffset(0, SIZE); 1126 1127 ByteBuffer bb = ByteBuffer.allocate(SIZE); 1128 bb.order(MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN); 1129 bs.fill(bb.putFloat(0, VALUE_2).array()); 1130 1131 int length = array.limit() - SIZE + 1; 1132 for (int i = 0; i < length; i++) { 1133 boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; 1134 1135 float v = MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) 1136 ? rotateLeft(VALUE_2, (i % SIZE) << 3) 1137 : rotateRight(VALUE_2, (i % SIZE) << 3); 1138 // Plain 1139 { 1140 float x = (float) vh.get(array, i); 1141 assertEquals(x, v, "get float value"); 1142 } 1143 1144 if (iAligned) { 1145 // Volatile 1146 { 1147 float x = (float) vh.getVolatile(array, i); 1148 assertEquals(x, v, "getVolatile float value"); 1149 } 1150 1151 // Lazy 1152 { 1153 float x = (float) vh.getAcquire(array, i); 1154 assertEquals(x, v, "getRelease float value"); 1155 } 1156 1157 // Opaque 1158 { 1159 float x = (float) vh.getOpaque(array, i); 1160 assertEquals(x, v, "getOpaque float value"); 1161 } 1162 } 1163 } 1164 } 1165 1166} 1167 1168