1 /*
   2  * Copyright (c) 2015, 2019, 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 #if[Value]
  25 /*
  26  * @test
  27  * @run testng/othervm -Diters=10    -XX:+EnableValhalla -Xint                   VarHandleTestAccess$Type$
  28  * @run testng/othervm -Diters=20000 -XX:+EnableValhalla -XX:TieredStopAtLevel=1 VarHandleTestAccess$Type$
  29  * @run testng/othervm -Diters=20000 -XX:+EnableValhalla                         VarHandleTestAccess$Type$
  30  * @run testng/othervm -Diters=20000 -XX:+EnableValhalla -XX:-TieredCompilation  VarHandleTestAccess$Type$
  31  */
  32 #else[Value]
  33 /*
  34  * @test
  35  * @run testng/othervm -Diters=10    -Xint                   VarHandleTestAccess$Type$
  36  * @run testng/othervm -Diters=20000 -XX:TieredStopAtLevel=1 VarHandleTestAccess$Type$
  37  * @run testng/othervm -Diters=20000                         VarHandleTestAccess$Type$
  38  * @run testng/othervm -Diters=20000 -XX:-TieredCompilation  VarHandleTestAccess$Type$
  39  */
  40 #end[Value]
  41 
  42 import org.testng.annotations.BeforeClass;
  43 import org.testng.annotations.DataProvider;
  44 import org.testng.annotations.Test;
  45 
  46 import java.lang.invoke.MethodHandles;
  47 import java.lang.invoke.VarHandle;
  48 import java.util.ArrayList;
  49 import java.util.Arrays;
  50 import java.util.List;
  51 
  52 import static org.testng.Assert.*;
  53 
  54 public class VarHandleTestAccess$Type$ extends VarHandleBaseTest {
  55     static final $type$ static_final_v = $value1$;
  56 
  57     static $type$ static_v;
  58 
  59     final $type$ final_v = $value1$;
  60 
  61     $type$ v;
  62 
  63     static final $type$ static_final_v2 = $value1$;
  64 
  65     static $type$ static_v2;
  66 
  67     final $type$ final_v2 = $value1$;
  68 
  69     $type$ v2;
  70 
  71     VarHandle vhFinalField;
  72 
  73     VarHandle vhField;
  74 
  75     VarHandle vhStaticField;
  76 
  77     VarHandle vhStaticFinalField;
  78 
  79     VarHandle vhArray;
  80 
  81 #if[String]
  82     VarHandle vhArrayObject;
  83 #end[String]
  84 #if[Value]
  85     VarHandle vhValueTypeField;
  86 #end[Value]
  87 
  88     VarHandle[] allocate(boolean same) {
  89         List<VarHandle> vhs = new ArrayList<>();
  90 
  91         String postfix = same ? "" : "2";
  92         VarHandle vh;
  93         try {
  94             vh = MethodHandles.lookup().findVarHandle(
  95                     VarHandleTestAccess$Type$.class, "final_v" + postfix, $type$.class);
  96             vhs.add(vh);
  97 
  98             vh = MethodHandles.lookup().findVarHandle(
  99                     VarHandleTestAccess$Type$.class, "v" + postfix, $type$.class);
 100             vhs.add(vh);
 101 
 102             vh = MethodHandles.lookup().findStaticVarHandle(
 103                 VarHandleTestAccess$Type$.class, "static_final_v" + postfix, $type$.class);
 104             vhs.add(vh);
 105 
 106             vh = MethodHandles.lookup().findStaticVarHandle(
 107                 VarHandleTestAccess$Type$.class, "static_v" + postfix, $type$.class);
 108             vhs.add(vh);
 109 
 110             if (same) {
 111                 vh = MethodHandles.arrayElementVarHandle($type$[].class);
 112             }
 113             else {
 114 #if[String]
 115                 vh = MethodHandles.arrayElementVarHandle(int[].class);
 116 #else[String]
 117                 vh = MethodHandles.arrayElementVarHandle(String[].class);
 118 #end[String]
 119             }
 120             vhs.add(vh);
 121         } catch (Exception e) {
 122             throw new InternalError(e);
 123         }
 124         return vhs.toArray(new VarHandle[0]);
 125     }
 126 
 127     @BeforeClass
 128     public void setup() throws Exception {
 129         vhFinalField = MethodHandles.lookup().findVarHandle(
 130                 VarHandleTestAccess$Type$.class, "final_v", $type$.class);
 131 
 132         vhField = MethodHandles.lookup().findVarHandle(
 133                 VarHandleTestAccess$Type$.class, "v", $type$.class);
 134 
 135         vhStaticFinalField = MethodHandles.lookup().findStaticVarHandle(
 136             VarHandleTestAccess$Type$.class, "static_final_v", $type$.class);
 137 
 138         vhStaticField = MethodHandles.lookup().findStaticVarHandle(
 139             VarHandleTestAccess$Type$.class, "static_v", $type$.class);
 140 
 141         vhArray = MethodHandles.arrayElementVarHandle($type$[].class);
 142 #if[String]
 143         vhArrayObject = MethodHandles.arrayElementVarHandle(Object[].class);
 144 #end[String]
 145 
 146 #if[Value]
 147         vhValueTypeField = MethodHandles.lookup().findVarHandle(
 148                     Value.class, "$type$_v", $type$.class);
 149 #end[Value]
 150     }
 151 
 152 
 153     @DataProvider
 154     public Object[][] varHandlesProvider() throws Exception {
 155         List<VarHandle> vhs = new ArrayList<>();
 156         vhs.add(vhField);
 157         vhs.add(vhStaticField);
 158         vhs.add(vhArray);
 159 
 160         return vhs.stream().map(tc -> new Object[]{tc}).toArray(Object[][]::new);
 161     }
 162 
 163     @Test
 164     public void testEquals() {
 165         VarHandle[] vhs1 = allocate(true);
 166         VarHandle[] vhs2 = allocate(true);
 167 
 168         for (int i = 0; i < vhs1.length; i++) {
 169             for (int j = 0; j < vhs1.length; j++) {
 170                 if (i != j) {
 171                     assertNotEquals(vhs1[i], vhs1[j]);
 172                     assertNotEquals(vhs1[i], vhs2[j]);
 173                 }
 174             }
 175         }
 176 
 177         VarHandle[] vhs3 = allocate(false);
 178         for (int i = 0; i < vhs1.length; i++) {
 179             assertNotEquals(vhs1[i], vhs3[i]);
 180         }
 181     }
 182 
 183     @Test(dataProvider = "varHandlesProvider")
 184     public void testIsAccessModeSupported(VarHandle vh) {
 185         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET));
 186         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET));
 187         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE));
 188         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE));
 189         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE));
 190         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE));
 191         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE));
 192         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE));
 193 
 194 #if[CAS]
 195         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET));
 196         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE));
 197         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE));
 198         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE));
 199         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN));
 200         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET));
 201         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE));
 202         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE));
 203         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET));
 204         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE));
 205         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE));
 206 #else[CAS]
 207         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET));
 208         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE));
 209         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE));
 210         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE));
 211         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN));
 212         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET));
 213         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE));
 214         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE));
 215         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET));
 216         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE));
 217         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE));
 218 #end[CAS]
 219 
 220 #if[AtomicAdd]
 221         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD));
 222         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE));
 223         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE));
 224 #else[AtomicAdd]
 225         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD));
 226         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE));
 227         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE));
 228 #end[AtomicAdd]
 229 
 230 #if[Bitwise]
 231         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR));
 232         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE));
 233         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE));
 234         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND));
 235         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE));
 236         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE));
 237         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR));
 238         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE));
 239         assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE));
 240 #else[Bitwise]
 241         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR));
 242         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE));
 243         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE));
 244         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND));
 245         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE));
 246         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE));
 247         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR));
 248         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE));
 249         assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE));
 250 #end[Bitwise]
 251     }
 252 
 253 
 254     @DataProvider
 255     public Object[][] typesProvider() throws Exception {
 256         List<Object[]> types = new ArrayList<>();
 257         types.add(new Object[] {vhField, Arrays.asList(VarHandleTestAccess$Type$.class)});
 258         types.add(new Object[] {vhStaticField, Arrays.asList()});
 259         types.add(new Object[] {vhArray, Arrays.asList($type$[].class, int.class)});
 260 
 261         return types.stream().toArray(Object[][]::new);
 262     }
 263 
 264     @Test(dataProvider = "typesProvider")
 265     public void testTypes(VarHandle vh, List<Class<?>> pts) {
 266         assertEquals(vh.varType(), $type$.class);
 267 
 268         assertEquals(vh.coordinateTypes(), pts);
 269 
 270         testTypes(vh);
 271     }
 272 
 273 
 274     @Test
 275     public void testLookupInstanceToStatic() {
 276         checkIAE("Lookup of static final field to instance final field", () -> {
 277             MethodHandles.lookup().findStaticVarHandle(
 278                     VarHandleTestAccess$Type$.class, "final_v", $type$.class);
 279         });
 280 
 281         checkIAE("Lookup of static field to instance field", () -> {
 282             MethodHandles.lookup().findStaticVarHandle(
 283                     VarHandleTestAccess$Type$.class, "v", $type$.class);
 284         });
 285     }
 286 
 287     @Test
 288     public void testLookupStaticToInstance() {
 289         checkIAE("Lookup of instance final field to static final field", () -> {
 290             MethodHandles.lookup().findVarHandle(
 291                 VarHandleTestAccess$Type$.class, "static_final_v", $type$.class);
 292         });
 293 
 294         checkIAE("Lookup of instance field to static field", () -> {
 295             vhStaticField = MethodHandles.lookup().findVarHandle(
 296                 VarHandleTestAccess$Type$.class, "static_v", $type$.class);
 297         });
 298     }
 299 
 300 
 301     @DataProvider
 302     public Object[][] accessTestCaseProvider() throws Exception {
 303         List<AccessTestCase<?>> cases = new ArrayList<>();
 304 
 305         cases.add(new VarHandleAccessTestCase("Instance final field",
 306                                               vhFinalField, vh -> testInstanceFinalField(this, vh)));
 307         cases.add(new VarHandleAccessTestCase("Instance final field unsupported",
 308                                               vhFinalField, vh -> testInstanceFinalFieldUnsupported(this, vh),
 309                                               false));
 310 
 311         cases.add(new VarHandleAccessTestCase("Static final field",
 312                                               vhStaticFinalField, VarHandleTestAccess$Type$::testStaticFinalField));
 313         cases.add(new VarHandleAccessTestCase("Static final field unsupported",
 314                                               vhStaticFinalField, VarHandleTestAccess$Type$::testStaticFinalFieldUnsupported,
 315                                               false));
 316 
 317         cases.add(new VarHandleAccessTestCase("Instance field",
 318                                               vhField, vh -> testInstanceField(this, vh)));
 319         cases.add(new VarHandleAccessTestCase("Instance field unsupported",
 320                                               vhField, vh -> testInstanceFieldUnsupported(this, vh),
 321                                               false));
 322 
 323         cases.add(new VarHandleAccessTestCase("Static field",
 324                                               vhStaticField, VarHandleTestAccess$Type$::testStaticField));
 325         cases.add(new VarHandleAccessTestCase("Static field unsupported",
 326                                               vhStaticField, VarHandleTestAccess$Type$::testStaticFieldUnsupported,
 327                                               false));
 328 
 329         cases.add(new VarHandleAccessTestCase("Array",
 330                                               vhArray, VarHandleTestAccess$Type$::testArray));
 331 #if[String]
 332         cases.add(new VarHandleAccessTestCase("Array Object[]",
 333                                               vhArrayObject, VarHandleTestAccess$Type$::testArray));
 334 #end[String]
 335         cases.add(new VarHandleAccessTestCase("Array unsupported",
 336                                               vhArray, VarHandleTestAccess$Type$::testArrayUnsupported,
 337                                               false));
 338         cases.add(new VarHandleAccessTestCase("Array index out of bounds",
 339                                               vhArray, VarHandleTestAccess$Type$::testArrayIndexOutOfBounds,
 340                                               false));
 341 #if[String]
 342         cases.add(new VarHandleAccessTestCase("Array store exception",
 343                                               vhArrayObject, VarHandleTestAccess$Type$::testArrayStoreException,
 344                                               false));
 345 #end[String]
 346 #if[Value]
 347         cases.add(new VarHandleAccessTestCase("Value type field",
 348                                               vhValueTypeField, vh -> testValueTypeField(Value.getInstance(), vh)));
 349         cases.add(new VarHandleAccessTestCase("Value type field unsupported",
 350                                               vhValueTypeField, vh -> testValueTypeFieldUnsupported(Value.getInstance(), vh),
 351                                               false));
 352 #end[Value]
 353         // Work around issue with jtreg summary reporting which truncates
 354         // the String result of Object.toString to 30 characters, hence
 355         // the first dummy argument
 356         return cases.stream().map(tc -> new Object[]{tc.toString(), tc}).toArray(Object[][]::new);
 357     }
 358 
 359     @Test(dataProvider = "accessTestCaseProvider")
 360     public <T> void testAccess(String desc, AccessTestCase<T> atc) throws Throwable {
 361         T t = atc.get();
 362         int iters = atc.requiresLoop() ? ITERS : 1;
 363         for (int c = 0; c < iters; c++) {
 364             atc.testAccess(t);
 365         }
 366     }
 367 
 368 
 369 
 370 
 371     static void testInstanceFinalField(VarHandleTestAccess$Type$ recv, VarHandle vh) {
 372         // Plain
 373         {
 374             $type$ x = ($type$) vh.get(recv);
 375             assertEquals(x, $value1$, "get $type$ value");
 376         }
 377 
 378 
 379         // Volatile
 380         {
 381             $type$ x = ($type$) vh.getVolatile(recv);
 382             assertEquals(x, $value1$, "getVolatile $type$ value");
 383         }
 384 
 385         // Lazy
 386         {
 387             $type$ x = ($type$) vh.getAcquire(recv);
 388             assertEquals(x, $value1$, "getRelease $type$ value");
 389         }
 390 
 391         // Opaque
 392         {
 393             $type$ x = ($type$) vh.getOpaque(recv);
 394             assertEquals(x, $value1$, "getOpaque $type$ value");
 395         }
 396     }
 397 
 398     static void testInstanceFinalFieldUnsupported(VarHandleTestAccess$Type$ recv, VarHandle vh) {
 399         checkUOE(() -> {
 400             vh.set(recv, $value2$);
 401         });
 402 
 403         checkUOE(() -> {
 404             vh.setVolatile(recv, $value2$);
 405         });
 406 
 407         checkUOE(() -> {
 408             vh.setRelease(recv, $value2$);
 409         });
 410 
 411         checkUOE(() -> {
 412             vh.setOpaque(recv, $value2$);
 413         });
 414 
 415 #if[!CAS]
 416         checkUOE(() -> {
 417             boolean r = vh.compareAndSet(recv, $value1$, $value2$);
 418         });
 419 
 420         checkUOE(() -> {
 421             $type$ r = ($type$) vh.compareAndExchange(recv, $value1$, $value2$);
 422         });
 423 
 424         checkUOE(() -> {
 425             $type$ r = ($type$) vh.compareAndExchangeAcquire(recv, $value1$, $value2$);
 426         });
 427 
 428         checkUOE(() -> {
 429             $type$ r = ($type$) vh.compareAndExchangeRelease(recv, $value1$, $value2$);
 430         });
 431 
 432         checkUOE(() -> {
 433             boolean r = vh.weakCompareAndSetPlain(recv, $value1$, $value2$);
 434         });
 435 
 436         checkUOE(() -> {
 437             boolean r = vh.weakCompareAndSet(recv, $value1$, $value2$);
 438         });
 439 
 440         checkUOE(() -> {
 441             boolean r = vh.weakCompareAndSetAcquire(recv, $value1$, $value2$);
 442         });
 443 
 444         checkUOE(() -> {
 445             boolean r = vh.weakCompareAndSetRelease(recv, $value1$, $value2$);
 446         });
 447 
 448         checkUOE(() -> {
 449             $type$ r = ($type$) vh.getAndSet(recv, $value1$);
 450         });
 451 
 452         checkUOE(() -> {
 453             $type$ r = ($type$) vh.getAndSetAcquire(recv, $value1$);
 454         });
 455 
 456         checkUOE(() -> {
 457             $type$ r = ($type$) vh.getAndSetRelease(recv, $value1$);
 458         });
 459 #end[CAS]
 460 
 461 #if[!AtomicAdd]
 462         checkUOE(() -> {
 463             $type$ o = ($type$) vh.getAndAdd(recv, $value1$);
 464         });
 465 
 466         checkUOE(() -> {
 467             $type$ o = ($type$) vh.getAndAddAcquire(recv, $value1$);
 468         });
 469 
 470         checkUOE(() -> {
 471             $type$ o = ($type$) vh.getAndAddRelease(recv, $value1$);
 472         });
 473 #end[AtomicAdd]
 474 
 475 #if[!Bitwise]
 476         checkUOE(() -> {
 477             $type$ o = ($type$) vh.getAndBitwiseOr(recv, $value1$);
 478         });
 479 
 480         checkUOE(() -> {
 481             $type$ o = ($type$) vh.getAndBitwiseOrAcquire(recv, $value1$);
 482         });
 483 
 484         checkUOE(() -> {
 485             $type$ o = ($type$) vh.getAndBitwiseOrRelease(recv, $value1$);
 486         });
 487 
 488         checkUOE(() -> {
 489             $type$ o = ($type$) vh.getAndBitwiseAnd(recv, $value1$);
 490         });
 491 
 492         checkUOE(() -> {
 493             $type$ o = ($type$) vh.getAndBitwiseAndAcquire(recv, $value1$);
 494         });
 495 
 496         checkUOE(() -> {
 497             $type$ o = ($type$) vh.getAndBitwiseAndRelease(recv, $value1$);
 498         });
 499 
 500         checkUOE(() -> {
 501             $type$ o = ($type$) vh.getAndBitwiseXor(recv, $value1$);
 502         });
 503 
 504         checkUOE(() -> {
 505             $type$ o = ($type$) vh.getAndBitwiseXorAcquire(recv, $value1$);
 506         });
 507 
 508         checkUOE(() -> {
 509             $type$ o = ($type$) vh.getAndBitwiseXorRelease(recv, $value1$);
 510         });
 511 #end[Bitwise]
 512     }
 513 
 514 #if[Value]
 515     static void testValueTypeField(Value recv, VarHandle vh) {
 516         // Plain
 517         {
 518             $type$ x = ($type$) vh.get(recv);
 519             assertEquals(x, $value1$, "get $type$ value");
 520         }
 521     }
 522 
 523     static void testValueTypeFieldUnsupported(Value recv, VarHandle vh) {
 524         checkUOE(() -> {
 525             vh.set(recv, $value2$);
 526         });
 527     }
 528 #end[Value]
 529 
 530     static void testStaticFinalField(VarHandle vh) {
 531         // Plain
 532         {
 533             $type$ x = ($type$) vh.get();
 534             assertEquals(x, $value1$, "get $type$ value");
 535         }
 536 
 537 
 538         // Volatile
 539         {
 540             $type$ x = ($type$) vh.getVolatile();
 541             assertEquals(x, $value1$, "getVolatile $type$ value");
 542         }
 543 
 544         // Lazy
 545         {
 546             $type$ x = ($type$) vh.getAcquire();
 547             assertEquals(x, $value1$, "getRelease $type$ value");
 548         }
 549 
 550         // Opaque
 551         {
 552             $type$ x = ($type$) vh.getOpaque();
 553             assertEquals(x, $value1$, "getOpaque $type$ value");
 554         }
 555     }
 556 
 557     static void testStaticFinalFieldUnsupported(VarHandle vh) {
 558         checkUOE(() -> {
 559             vh.set($value2$);
 560         });
 561 
 562         checkUOE(() -> {
 563             vh.setVolatile($value2$);
 564         });
 565 
 566         checkUOE(() -> {
 567             vh.setRelease($value2$);
 568         });
 569 
 570         checkUOE(() -> {
 571             vh.setOpaque($value2$);
 572         });
 573 
 574 #if[!CAS]
 575         checkUOE(() -> {
 576             boolean r = vh.compareAndSet($value1$, $value2$);
 577         });
 578 
 579         checkUOE(() -> {
 580             $type$ r = ($type$) vh.compareAndExchange($value1$, $value2$);
 581         });
 582 
 583         checkUOE(() -> {
 584             $type$ r = ($type$) vh.compareAndExchangeAcquire($value1$, $value2$);
 585         });
 586 
 587         checkUOE(() -> {
 588             $type$ r = ($type$) vh.compareAndExchangeRelease($value1$, $value2$);
 589         });
 590 
 591         checkUOE(() -> {
 592             boolean r = vh.weakCompareAndSetPlain($value1$, $value2$);
 593         });
 594 
 595         checkUOE(() -> {
 596             boolean r = vh.weakCompareAndSet($value1$, $value2$);
 597         });
 598 
 599         checkUOE(() -> {
 600             boolean r = vh.weakCompareAndSetAcquire($value1$, $value2$);
 601         });
 602 
 603         checkUOE(() -> {
 604             boolean r = vh.weakCompareAndSetRelease($value1$, $value2$);
 605         });
 606 
 607         checkUOE(() -> {
 608             $type$ r = ($type$) vh.getAndSet($value1$);
 609         });
 610 
 611         checkUOE(() -> {
 612             $type$ r = ($type$) vh.getAndSetAcquire($value1$);
 613         });
 614 
 615         checkUOE(() -> {
 616             $type$ r = ($type$) vh.getAndSetRelease($value1$);
 617         });
 618 #end[CAS]
 619 
 620 #if[!AtomicAdd]
 621         checkUOE(() -> {
 622             $type$ o = ($type$) vh.getAndAdd($value1$);
 623         });
 624 
 625         checkUOE(() -> {
 626             $type$ o = ($type$) vh.getAndAddAcquire($value1$);
 627         });
 628 
 629         checkUOE(() -> {
 630             $type$ o = ($type$) vh.getAndAddRelease($value1$);
 631         });
 632 #end[AtomicAdd]
 633 
 634 #if[!Bitwise]
 635         checkUOE(() -> {
 636             $type$ o = ($type$) vh.getAndBitwiseOr($value1$);
 637         });
 638 
 639         checkUOE(() -> {
 640             $type$ o = ($type$) vh.getAndBitwiseOrAcquire($value1$);
 641         });
 642 
 643         checkUOE(() -> {
 644             $type$ o = ($type$) vh.getAndBitwiseOrRelease($value1$);
 645         });
 646 
 647         checkUOE(() -> {
 648             $type$ o = ($type$) vh.getAndBitwiseAnd($value1$);
 649         });
 650 
 651         checkUOE(() -> {
 652             $type$ o = ($type$) vh.getAndBitwiseAndAcquire($value1$);
 653         });
 654 
 655         checkUOE(() -> {
 656             $type$ o = ($type$) vh.getAndBitwiseAndRelease($value1$);
 657         });
 658 
 659         checkUOE(() -> {
 660             $type$ o = ($type$) vh.getAndBitwiseXor($value1$);
 661         });
 662 
 663         checkUOE(() -> {
 664             $type$ o = ($type$) vh.getAndBitwiseXorAcquire($value1$);
 665         });
 666 
 667         checkUOE(() -> {
 668             $type$ o = ($type$) vh.getAndBitwiseXorRelease($value1$);
 669         });
 670 #end[Bitwise]
 671     }
 672 
 673 
 674     static void testInstanceField(VarHandleTestAccess$Type$ recv, VarHandle vh) {
 675         // Plain
 676         {
 677             vh.set(recv, $value1$);
 678             $type$ x = ($type$) vh.get(recv);
 679             assertEquals(x, $value1$, "set $type$ value");
 680         }
 681 
 682 
 683         // Volatile
 684         {
 685             vh.setVolatile(recv, $value2$);
 686             $type$ x = ($type$) vh.getVolatile(recv);
 687             assertEquals(x, $value2$, "setVolatile $type$ value");
 688         }
 689 
 690         // Lazy
 691         {
 692             vh.setRelease(recv, $value1$);
 693             $type$ x = ($type$) vh.getAcquire(recv);
 694             assertEquals(x, $value1$, "setRelease $type$ value");
 695         }
 696 
 697         // Opaque
 698         {
 699             vh.setOpaque(recv, $value2$);
 700             $type$ x = ($type$) vh.getOpaque(recv);
 701             assertEquals(x, $value2$, "setOpaque $type$ value");
 702         }
 703 
 704 #if[CAS]
 705         vh.set(recv, $value1$);
 706 
 707         // Compare
 708         {
 709             boolean r = vh.compareAndSet(recv, $value1$, $value2$);
 710             assertEquals(r, true, "success compareAndSet $type$");
 711             $type$ x = ($type$) vh.get(recv);
 712             assertEquals(x, $value2$, "success compareAndSet $type$ value");
 713         }
 714 
 715         {
 716             boolean r = vh.compareAndSet(recv, $value1$, $value3$);
 717             assertEquals(r, false, "failing compareAndSet $type$");
 718             $type$ x = ($type$) vh.get(recv);
 719             assertEquals(x, $value2$, "failing compareAndSet $type$ value");
 720         }
 721 
 722         {
 723             $type$ r = ($type$) vh.compareAndExchange(recv, $value2$, $value1$);
 724             assertEquals(r, $value2$, "success compareAndExchange $type$");
 725             $type$ x = ($type$) vh.get(recv);
 726             assertEquals(x, $value1$, "success compareAndExchange $type$ value");
 727         }
 728 
 729         {
 730             $type$ r = ($type$) vh.compareAndExchange(recv, $value2$, $value3$);
 731             assertEquals(r, $value1$, "failing compareAndExchange $type$");
 732             $type$ x = ($type$) vh.get(recv);
 733             assertEquals(x, $value1$, "failing compareAndExchange $type$ value");
 734         }
 735 
 736         {
 737             $type$ r = ($type$) vh.compareAndExchangeAcquire(recv, $value1$, $value2$);
 738             assertEquals(r, $value1$, "success compareAndExchangeAcquire $type$");
 739             $type$ x = ($type$) vh.get(recv);
 740             assertEquals(x, $value2$, "success compareAndExchangeAcquire $type$ value");
 741         }
 742 
 743         {
 744             $type$ r = ($type$) vh.compareAndExchangeAcquire(recv, $value1$, $value3$);
 745             assertEquals(r, $value2$, "failing compareAndExchangeAcquire $type$");
 746             $type$ x = ($type$) vh.get(recv);
 747             assertEquals(x, $value2$, "failing compareAndExchangeAcquire $type$ value");
 748         }
 749 
 750         {
 751             $type$ r = ($type$) vh.compareAndExchangeRelease(recv, $value2$, $value1$);
 752             assertEquals(r, $value2$, "success compareAndExchangeRelease $type$");
 753             $type$ x = ($type$) vh.get(recv);
 754             assertEquals(x, $value1$, "success compareAndExchangeRelease $type$ value");
 755         }
 756 
 757         {
 758             $type$ r = ($type$) vh.compareAndExchangeRelease(recv, $value2$, $value3$);
 759             assertEquals(r, $value1$, "failing compareAndExchangeRelease $type$");
 760             $type$ x = ($type$) vh.get(recv);
 761             assertEquals(x, $value1$, "failing compareAndExchangeRelease $type$ value");
 762         }
 763 
 764         {
 765             boolean success = false;
 766             for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
 767                 success = vh.weakCompareAndSetPlain(recv, $value1$, $value2$);
 768             }
 769             assertEquals(success, true, "weakCompareAndSetPlain $type$");
 770             $type$ x = ($type$) vh.get(recv);
 771             assertEquals(x, $value2$, "weakCompareAndSetPlain $type$ value");
 772         }
 773 
 774         {
 775             boolean success = false;
 776             for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
 777                 success = vh.weakCompareAndSetAcquire(recv, $value2$, $value1$);
 778             }
 779             assertEquals(success, true, "weakCompareAndSetAcquire $type$");
 780             $type$ x = ($type$) vh.get(recv);
 781             assertEquals(x, $value1$, "weakCompareAndSetAcquire $type$");
 782         }
 783 
 784         {
 785             boolean success = false;
 786             for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
 787                 success = vh.weakCompareAndSetRelease(recv, $value1$, $value2$);
 788             }
 789             assertEquals(success, true, "weakCompareAndSetRelease $type$");
 790             $type$ x = ($type$) vh.get(recv);
 791             assertEquals(x, $value2$, "weakCompareAndSetRelease $type$");
 792         }
 793 
 794         {
 795             boolean success = false;
 796             for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
 797                 success = vh.weakCompareAndSet(recv, $value2$, $value1$);
 798             }
 799             assertEquals(success, true, "weakCompareAndSet $type$");
 800             $type$ x = ($type$) vh.get(recv);
 801             assertEquals(x, $value1$, "weakCompareAndSet $type$ value");
 802         }
 803 
 804         // Compare set and get
 805         {
 806             vh.set(recv, $value1$);
 807 
 808             $type$ o = ($type$) vh.getAndSet(recv, $value2$);
 809             assertEquals(o, $value1$, "getAndSet $type$");
 810             $type$ x = ($type$) vh.get(recv);
 811             assertEquals(x, $value2$, "getAndSet $type$ value");
 812         }
 813 
 814         {
 815             vh.set(recv, $value1$);
 816 
 817             $type$ o = ($type$) vh.getAndSetAcquire(recv, $value2$);
 818             assertEquals(o, $value1$, "getAndSetAcquire $type$");
 819             $type$ x = ($type$) vh.get(recv);
 820             assertEquals(x, $value2$, "getAndSetAcquire $type$ value");
 821         }
 822 
 823         {
 824             vh.set(recv, $value1$);
 825 
 826             $type$ o = ($type$) vh.getAndSetRelease(recv, $value2$);
 827             assertEquals(o, $value1$, "getAndSetRelease $type$");
 828             $type$ x = ($type$) vh.get(recv);
 829             assertEquals(x, $value2$, "getAndSetRelease $type$ value");
 830         }
 831 #end[CAS]
 832 
 833 #if[AtomicAdd]
 834         // get and add, add and get
 835         {
 836             vh.set(recv, $value1$);
 837 
 838             $type$ o = ($type$) vh.getAndAdd(recv, $value2$);
 839             assertEquals(o, $value1$, "getAndAdd $type$");
 840             $type$ x = ($type$) vh.get(recv);
 841             assertEquals(x, ($type$)($value1$ + $value2$), "getAndAdd $type$ value");
 842         }
 843 
 844         {
 845             vh.set(recv, $value1$);
 846 
 847             $type$ o = ($type$) vh.getAndAddAcquire(recv, $value2$);
 848             assertEquals(o, $value1$, "getAndAddAcquire $type$");
 849             $type$ x = ($type$) vh.get(recv);
 850             assertEquals(x, ($type$)($value1$ + $value2$), "getAndAddAcquire $type$ value");
 851         }
 852 
 853         {
 854             vh.set(recv, $value1$);
 855 
 856             $type$ o = ($type$) vh.getAndAddRelease(recv, $value2$);
 857             assertEquals(o, $value1$, "getAndAddRelease$type$");
 858             $type$ x = ($type$) vh.get(recv);
 859             assertEquals(x, ($type$)($value1$ + $value2$), "getAndAddRelease $type$ value");
 860         }
 861 #end[AtomicAdd]
 862 
 863 #if[Bitwise]
 864         // get and bitwise or
 865         {
 866             vh.set(recv, $value1$);
 867 
 868             $type$ o = ($type$) vh.getAndBitwiseOr(recv, $value2$);
 869             assertEquals(o, $value1$, "getAndBitwiseOr $type$");
 870             $type$ x = ($type$) vh.get(recv);
 871             assertEquals(x, ($type$)($value1$ | $value2$), "getAndBitwiseOr $type$ value");
 872         }
 873 
 874         {
 875             vh.set(recv, $value1$);
 876 
 877             $type$ o = ($type$) vh.getAndBitwiseOrAcquire(recv, $value2$);
 878             assertEquals(o, $value1$, "getAndBitwiseOrAcquire $type$");
 879             $type$ x = ($type$) vh.get(recv);
 880             assertEquals(x, ($type$)($value1$ | $value2$), "getAndBitwiseOrAcquire $type$ value");
 881         }
 882 
 883         {
 884             vh.set(recv, $value1$);
 885 
 886             $type$ o = ($type$) vh.getAndBitwiseOrRelease(recv, $value2$);
 887             assertEquals(o, $value1$, "getAndBitwiseOrRelease $type$");
 888             $type$ x = ($type$) vh.get(recv);
 889             assertEquals(x, ($type$)($value1$ | $value2$), "getAndBitwiseOrRelease $type$ value");
 890         }
 891 
 892         // get and bitwise and
 893         {
 894             vh.set(recv, $value1$);
 895 
 896             $type$ o = ($type$) vh.getAndBitwiseAnd(recv, $value2$);
 897             assertEquals(o, $value1$, "getAndBitwiseAnd $type$");
 898             $type$ x = ($type$) vh.get(recv);
 899             assertEquals(x, ($type$)($value1$ & $value2$), "getAndBitwiseAnd $type$ value");
 900         }
 901 
 902         {
 903             vh.set(recv, $value1$);
 904 
 905             $type$ o = ($type$) vh.getAndBitwiseAndAcquire(recv, $value2$);
 906             assertEquals(o, $value1$, "getAndBitwiseAndAcquire $type$");
 907             $type$ x = ($type$) vh.get(recv);
 908             assertEquals(x, ($type$)($value1$ & $value2$), "getAndBitwiseAndAcquire $type$ value");
 909         }
 910 
 911         {
 912             vh.set(recv, $value1$);
 913 
 914             $type$ o = ($type$) vh.getAndBitwiseAndRelease(recv, $value2$);
 915             assertEquals(o, $value1$, "getAndBitwiseAndRelease $type$");
 916             $type$ x = ($type$) vh.get(recv);
 917             assertEquals(x, ($type$)($value1$ & $value2$), "getAndBitwiseAndRelease $type$ value");
 918         }
 919 
 920         // get and bitwise xor
 921         {
 922             vh.set(recv, $value1$);
 923 
 924             $type$ o = ($type$) vh.getAndBitwiseXor(recv, $value2$);
 925             assertEquals(o, $value1$, "getAndBitwiseXor $type$");
 926             $type$ x = ($type$) vh.get(recv);
 927             assertEquals(x, ($type$)($value1$ ^ $value2$), "getAndBitwiseXor $type$ value");
 928         }
 929 
 930         {
 931             vh.set(recv, $value1$);
 932 
 933             $type$ o = ($type$) vh.getAndBitwiseXorAcquire(recv, $value2$);
 934             assertEquals(o, $value1$, "getAndBitwiseXorAcquire $type$");
 935             $type$ x = ($type$) vh.get(recv);
 936             assertEquals(x, ($type$)($value1$ ^ $value2$), "getAndBitwiseXorAcquire $type$ value");
 937         }
 938 
 939         {
 940             vh.set(recv, $value1$);
 941 
 942             $type$ o = ($type$) vh.getAndBitwiseXorRelease(recv, $value2$);
 943             assertEquals(o, $value1$, "getAndBitwiseXorRelease $type$");
 944             $type$ x = ($type$) vh.get(recv);
 945             assertEquals(x, ($type$)($value1$ ^ $value2$), "getAndBitwiseXorRelease $type$ value");
 946         }
 947 #end[Bitwise]
 948     }
 949 
 950     static void testInstanceFieldUnsupported(VarHandleTestAccess$Type$ recv, VarHandle vh) {
 951 #if[!CAS]
 952         checkUOE(() -> {
 953             boolean r = vh.compareAndSet(recv, $value1$, $value2$);
 954         });
 955 
 956         checkUOE(() -> {
 957             $type$ r = ($type$) vh.compareAndExchange(recv, $value1$, $value2$);
 958         });
 959 
 960         checkUOE(() -> {
 961             $type$ r = ($type$) vh.compareAndExchangeAcquire(recv, $value1$, $value2$);
 962         });
 963 
 964         checkUOE(() -> {
 965             $type$ r = ($type$) vh.compareAndExchangeRelease(recv, $value1$, $value2$);
 966         });
 967 
 968         checkUOE(() -> {
 969             boolean r = vh.weakCompareAndSetPlain(recv, $value1$, $value2$);
 970         });
 971 
 972         checkUOE(() -> {
 973             boolean r = vh.weakCompareAndSet(recv, $value1$, $value2$);
 974         });
 975 
 976         checkUOE(() -> {
 977             boolean r = vh.weakCompareAndSetAcquire(recv, $value1$, $value2$);
 978         });
 979 
 980         checkUOE(() -> {
 981             boolean r = vh.weakCompareAndSetRelease(recv, $value1$, $value2$);
 982         });
 983 
 984         checkUOE(() -> {
 985             $type$ r = ($type$) vh.getAndSet(recv, $value1$);
 986         });
 987 
 988         checkUOE(() -> {
 989             $type$ r = ($type$) vh.getAndSetAcquire(recv, $value1$);
 990         });
 991 
 992         checkUOE(() -> {
 993             $type$ r = ($type$) vh.getAndSetRelease(recv, $value1$);
 994         });
 995 #end[CAS]
 996 
 997 #if[!AtomicAdd]
 998         checkUOE(() -> {
 999             $type$ o = ($type$) vh.getAndAdd(recv, $value1$);
1000         });
1001 
1002         checkUOE(() -> {
1003             $type$ o = ($type$) vh.getAndAddAcquire(recv, $value1$);
1004         });
1005 
1006         checkUOE(() -> {
1007             $type$ o = ($type$) vh.getAndAddRelease(recv, $value1$);
1008         });
1009 #end[AtomicAdd]
1010 
1011 #if[!Bitwise]
1012         checkUOE(() -> {
1013             $type$ o = ($type$) vh.getAndBitwiseOr(recv, $value1$);
1014         });
1015 
1016         checkUOE(() -> {
1017             $type$ o = ($type$) vh.getAndBitwiseOrAcquire(recv, $value1$);
1018         });
1019 
1020         checkUOE(() -> {
1021             $type$ o = ($type$) vh.getAndBitwiseOrRelease(recv, $value1$);
1022         });
1023 
1024         checkUOE(() -> {
1025             $type$ o = ($type$) vh.getAndBitwiseAnd(recv, $value1$);
1026         });
1027 
1028         checkUOE(() -> {
1029             $type$ o = ($type$) vh.getAndBitwiseAndAcquire(recv, $value1$);
1030         });
1031 
1032         checkUOE(() -> {
1033             $type$ o = ($type$) vh.getAndBitwiseAndRelease(recv, $value1$);
1034         });
1035 
1036         checkUOE(() -> {
1037             $type$ o = ($type$) vh.getAndBitwiseXor(recv, $value1$);
1038         });
1039 
1040         checkUOE(() -> {
1041             $type$ o = ($type$) vh.getAndBitwiseXorAcquire(recv, $value1$);
1042         });
1043 
1044         checkUOE(() -> {
1045             $type$ o = ($type$) vh.getAndBitwiseXorRelease(recv, $value1$);
1046         });
1047 #end[Bitwise]
1048     }
1049 
1050 
1051     static void testStaticField(VarHandle vh) {
1052         // Plain
1053         {
1054             vh.set($value1$);
1055             $type$ x = ($type$) vh.get();
1056             assertEquals(x, $value1$, "set $type$ value");
1057         }
1058 
1059 
1060         // Volatile
1061         {
1062             vh.setVolatile($value2$);
1063             $type$ x = ($type$) vh.getVolatile();
1064             assertEquals(x, $value2$, "setVolatile $type$ value");
1065         }
1066 
1067         // Lazy
1068         {
1069             vh.setRelease($value1$);
1070             $type$ x = ($type$) vh.getAcquire();
1071             assertEquals(x, $value1$, "setRelease $type$ value");
1072         }
1073 
1074         // Opaque
1075         {
1076             vh.setOpaque($value2$);
1077             $type$ x = ($type$) vh.getOpaque();
1078             assertEquals(x, $value2$, "setOpaque $type$ value");
1079         }
1080 
1081 #if[CAS]
1082         vh.set($value1$);
1083 
1084         // Compare
1085         {
1086             boolean r = vh.compareAndSet($value1$, $value2$);
1087             assertEquals(r, true, "success compareAndSet $type$");
1088             $type$ x = ($type$) vh.get();
1089             assertEquals(x, $value2$, "success compareAndSet $type$ value");
1090         }
1091 
1092         {
1093             boolean r = vh.compareAndSet($value1$, $value3$);
1094             assertEquals(r, false, "failing compareAndSet $type$");
1095             $type$ x = ($type$) vh.get();
1096             assertEquals(x, $value2$, "failing compareAndSet $type$ value");
1097         }
1098 
1099         {
1100             $type$ r = ($type$) vh.compareAndExchange($value2$, $value1$);
1101             assertEquals(r, $value2$, "success compareAndExchange $type$");
1102             $type$ x = ($type$) vh.get();
1103             assertEquals(x, $value1$, "success compareAndExchange $type$ value");
1104         }
1105 
1106         {
1107             $type$ r = ($type$) vh.compareAndExchange($value2$, $value3$);
1108             assertEquals(r, $value1$, "failing compareAndExchange $type$");
1109             $type$ x = ($type$) vh.get();
1110             assertEquals(x, $value1$, "failing compareAndExchange $type$ value");
1111         }
1112 
1113         {
1114             $type$ r = ($type$) vh.compareAndExchangeAcquire($value1$, $value2$);
1115             assertEquals(r, $value1$, "success compareAndExchangeAcquire $type$");
1116             $type$ x = ($type$) vh.get();
1117             assertEquals(x, $value2$, "success compareAndExchangeAcquire $type$ value");
1118         }
1119 
1120         {
1121             $type$ r = ($type$) vh.compareAndExchangeAcquire($value1$, $value3$);
1122             assertEquals(r, $value2$, "failing compareAndExchangeAcquire $type$");
1123             $type$ x = ($type$) vh.get();
1124             assertEquals(x, $value2$, "failing compareAndExchangeAcquire $type$ value");
1125         }
1126 
1127         {
1128             $type$ r = ($type$) vh.compareAndExchangeRelease($value2$, $value1$);
1129             assertEquals(r, $value2$, "success compareAndExchangeRelease $type$");
1130             $type$ x = ($type$) vh.get();
1131             assertEquals(x, $value1$, "success compareAndExchangeRelease $type$ value");
1132         }
1133 
1134         {
1135             $type$ r = ($type$) vh.compareAndExchangeRelease($value2$, $value3$);
1136             assertEquals(r, $value1$, "failing compareAndExchangeRelease $type$");
1137             $type$ x = ($type$) vh.get();
1138             assertEquals(x, $value1$, "failing compareAndExchangeRelease $type$ value");
1139         }
1140 
1141         {
1142             boolean success = false;
1143             for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
1144                 success = vh.weakCompareAndSetPlain($value1$, $value2$);
1145             }
1146             assertEquals(success, true, "weakCompareAndSetPlain $type$");
1147             $type$ x = ($type$) vh.get();
1148             assertEquals(x, $value2$, "weakCompareAndSetPlain $type$ value");
1149         }
1150 
1151         {
1152             boolean success = false;
1153             for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
1154                 success = vh.weakCompareAndSetAcquire($value2$, $value1$);
1155             }
1156             assertEquals(success, true, "weakCompareAndSetAcquire $type$");
1157             $type$ x = ($type$) vh.get();
1158             assertEquals(x, $value1$, "weakCompareAndSetAcquire $type$");
1159         }
1160 
1161         {
1162             boolean success = false;
1163             for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
1164                 success = vh.weakCompareAndSetRelease($value1$, $value2$);
1165             }
1166             assertEquals(success, true, "weakCompareAndSetRelease $type$");
1167             $type$ x = ($type$) vh.get();
1168             assertEquals(x, $value2$, "weakCompareAndSetRelease $type$");
1169         }
1170 
1171         {
1172             boolean success = false;
1173             for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
1174                 success = vh.weakCompareAndSet($value2$, $value1$);
1175             }
1176             assertEquals(success, true, "weakCompareAndSet $type$");
1177             $type$ x = ($type$) vh.get();
1178             assertEquals(x, $value1$, "weakCompareAndSet $type$");
1179         }
1180 
1181         // Compare set and get
1182         {
1183             vh.set($value1$);
1184 
1185             $type$ o = ($type$) vh.getAndSet($value2$);
1186             assertEquals(o, $value1$, "getAndSet $type$");
1187             $type$ x = ($type$) vh.get();
1188             assertEquals(x, $value2$, "getAndSet $type$ value");
1189         }
1190 
1191         {
1192             vh.set($value1$);
1193 
1194             $type$ o = ($type$) vh.getAndSetAcquire($value2$);
1195             assertEquals(o, $value1$, "getAndSetAcquire $type$");
1196             $type$ x = ($type$) vh.get();
1197             assertEquals(x, $value2$, "getAndSetAcquire $type$ value");
1198         }
1199 
1200         {
1201             vh.set($value1$);
1202 
1203             $type$ o = ($type$) vh.getAndSetRelease($value2$);
1204             assertEquals(o, $value1$, "getAndSetRelease $type$");
1205             $type$ x = ($type$) vh.get();
1206             assertEquals(x, $value2$, "getAndSetRelease $type$ value");
1207         }
1208 #end[CAS]
1209 
1210 #if[AtomicAdd]
1211         // get and add, add and get
1212         {
1213             vh.set($value1$);
1214 
1215             $type$ o = ($type$) vh.getAndAdd($value2$);
1216             assertEquals(o, $value1$, "getAndAdd $type$");
1217             $type$ x = ($type$) vh.get();
1218             assertEquals(x, ($type$)($value1$ + $value2$), "getAndAdd $type$ value");
1219         }
1220 
1221         {
1222             vh.set($value1$);
1223 
1224             $type$ o = ($type$) vh.getAndAddAcquire($value2$);
1225             assertEquals(o, $value1$, "getAndAddAcquire $type$");
1226             $type$ x = ($type$) vh.get();
1227             assertEquals(x, ($type$)($value1$ + $value2$), "getAndAddAcquire $type$ value");
1228         }
1229 
1230         {
1231             vh.set($value1$);
1232 
1233             $type$ o = ($type$) vh.getAndAddRelease($value2$);
1234             assertEquals(o, $value1$, "getAndAddRelease$type$");
1235             $type$ x = ($type$) vh.get();
1236             assertEquals(x, ($type$)($value1$ + $value2$), "getAndAddRelease $type$ value");
1237         }
1238 #end[AtomicAdd]
1239 
1240 #if[Bitwise]
1241         // get and bitwise or
1242         {
1243             vh.set($value1$);
1244 
1245             $type$ o = ($type$) vh.getAndBitwiseOr($value2$);
1246             assertEquals(o, $value1$, "getAndBitwiseOr $type$");
1247             $type$ x = ($type$) vh.get();
1248             assertEquals(x, ($type$)($value1$ | $value2$), "getAndBitwiseOr $type$ value");
1249         }
1250 
1251         {
1252             vh.set($value1$);
1253 
1254             $type$ o = ($type$) vh.getAndBitwiseOrAcquire($value2$);
1255             assertEquals(o, $value1$, "getAndBitwiseOrAcquire $type$");
1256             $type$ x = ($type$) vh.get();
1257             assertEquals(x, ($type$)($value1$ | $value2$), "getAndBitwiseOrAcquire $type$ value");
1258         }
1259 
1260         {
1261             vh.set($value1$);
1262 
1263             $type$ o = ($type$) vh.getAndBitwiseOrRelease($value2$);
1264             assertEquals(o, $value1$, "getAndBitwiseOrRelease $type$");
1265             $type$ x = ($type$) vh.get();
1266             assertEquals(x, ($type$)($value1$ | $value2$), "getAndBitwiseOrRelease $type$ value");
1267         }
1268 
1269         // get and bitwise and
1270         {
1271             vh.set($value1$);
1272 
1273             $type$ o = ($type$) vh.getAndBitwiseAnd($value2$);
1274             assertEquals(o, $value1$, "getAndBitwiseAnd $type$");
1275             $type$ x = ($type$) vh.get();
1276             assertEquals(x, ($type$)($value1$ & $value2$), "getAndBitwiseAnd $type$ value");
1277         }
1278 
1279         {
1280             vh.set($value1$);
1281 
1282             $type$ o = ($type$) vh.getAndBitwiseAndAcquire($value2$);
1283             assertEquals(o, $value1$, "getAndBitwiseAndAcquire $type$");
1284             $type$ x = ($type$) vh.get();
1285             assertEquals(x, ($type$)($value1$ & $value2$), "getAndBitwiseAndAcquire $type$ value");
1286         }
1287 
1288         {
1289             vh.set($value1$);
1290 
1291             $type$ o = ($type$) vh.getAndBitwiseAndRelease($value2$);
1292             assertEquals(o, $value1$, "getAndBitwiseAndRelease $type$");
1293             $type$ x = ($type$) vh.get();
1294             assertEquals(x, ($type$)($value1$ & $value2$), "getAndBitwiseAndRelease $type$ value");
1295         }
1296 
1297         // get and bitwise xor
1298         {
1299             vh.set($value1$);
1300 
1301             $type$ o = ($type$) vh.getAndBitwiseXor($value2$);
1302             assertEquals(o, $value1$, "getAndBitwiseXor $type$");
1303             $type$ x = ($type$) vh.get();
1304             assertEquals(x, ($type$)($value1$ ^ $value2$), "getAndBitwiseXor $type$ value");
1305         }
1306 
1307         {
1308             vh.set($value1$);
1309 
1310             $type$ o = ($type$) vh.getAndBitwiseXorAcquire($value2$);
1311             assertEquals(o, $value1$, "getAndBitwiseXorAcquire $type$");
1312             $type$ x = ($type$) vh.get();
1313             assertEquals(x, ($type$)($value1$ ^ $value2$), "getAndBitwiseXorAcquire $type$ value");
1314         }
1315 
1316         {
1317             vh.set($value1$);
1318 
1319             $type$ o = ($type$) vh.getAndBitwiseXorRelease($value2$);
1320             assertEquals(o, $value1$, "getAndBitwiseXorRelease $type$");
1321             $type$ x = ($type$) vh.get();
1322             assertEquals(x, ($type$)($value1$ ^ $value2$), "getAndBitwiseXorRelease $type$ value");
1323         }
1324 #end[Bitwise]
1325     }
1326 
1327     static void testStaticFieldUnsupported(VarHandle vh) {
1328 #if[!CAS]
1329         checkUOE(() -> {
1330             boolean r = vh.compareAndSet($value1$, $value2$);
1331         });
1332 
1333         checkUOE(() -> {
1334             $type$ r = ($type$) vh.compareAndExchange($value1$, $value2$);
1335         });
1336 
1337         checkUOE(() -> {
1338             $type$ r = ($type$) vh.compareAndExchangeAcquire($value1$, $value2$);
1339         });
1340 
1341         checkUOE(() -> {
1342             $type$ r = ($type$) vh.compareAndExchangeRelease($value1$, $value2$);
1343         });
1344 
1345         checkUOE(() -> {
1346             boolean r = vh.weakCompareAndSetPlain($value1$, $value2$);
1347         });
1348 
1349         checkUOE(() -> {
1350             boolean r = vh.weakCompareAndSet($value1$, $value2$);
1351         });
1352 
1353         checkUOE(() -> {
1354             boolean r = vh.weakCompareAndSetAcquire($value1$, $value2$);
1355         });
1356 
1357         checkUOE(() -> {
1358             boolean r = vh.weakCompareAndSetRelease($value1$, $value2$);
1359         });
1360 
1361         checkUOE(() -> {
1362             $type$ r = ($type$) vh.getAndSet($value1$);
1363         });
1364 
1365         checkUOE(() -> {
1366             $type$ r = ($type$) vh.getAndSetAcquire($value1$);
1367         });
1368 
1369         checkUOE(() -> {
1370             $type$ r = ($type$) vh.getAndSetRelease($value1$);
1371         });
1372 #end[CAS]
1373 
1374 #if[!AtomicAdd]
1375         checkUOE(() -> {
1376             $type$ o = ($type$) vh.getAndAdd($value1$);
1377         });
1378 
1379         checkUOE(() -> {
1380             $type$ o = ($type$) vh.getAndAddAcquire($value1$);
1381         });
1382 
1383         checkUOE(() -> {
1384             $type$ o = ($type$) vh.getAndAddRelease($value1$);
1385         });
1386 #end[AtomicAdd]
1387 
1388 #if[!Bitwise]
1389         checkUOE(() -> {
1390             $type$ o = ($type$) vh.getAndBitwiseOr($value1$);
1391         });
1392 
1393         checkUOE(() -> {
1394             $type$ o = ($type$) vh.getAndBitwiseOrAcquire($value1$);
1395         });
1396 
1397         checkUOE(() -> {
1398             $type$ o = ($type$) vh.getAndBitwiseOrRelease($value1$);
1399         });
1400 
1401         checkUOE(() -> {
1402             $type$ o = ($type$) vh.getAndBitwiseAnd($value1$);
1403         });
1404 
1405         checkUOE(() -> {
1406             $type$ o = ($type$) vh.getAndBitwiseAndAcquire($value1$);
1407         });
1408 
1409         checkUOE(() -> {
1410             $type$ o = ($type$) vh.getAndBitwiseAndRelease($value1$);
1411         });
1412 
1413         checkUOE(() -> {
1414             $type$ o = ($type$) vh.getAndBitwiseXor($value1$);
1415         });
1416 
1417         checkUOE(() -> {
1418             $type$ o = ($type$) vh.getAndBitwiseXorAcquire($value1$);
1419         });
1420 
1421         checkUOE(() -> {
1422             $type$ o = ($type$) vh.getAndBitwiseXorRelease($value1$);
1423         });
1424 #end[Bitwise]
1425     }
1426 
1427 
1428     static void testArray(VarHandle vh) {
1429         $type$[] array = new $type$[10];
1430 
1431         for (int i = 0; i < array.length; i++) {
1432             // Plain
1433             {
1434                 vh.set(array, i, $value1$);
1435                 $type$ x = ($type$) vh.get(array, i);
1436                 assertEquals(x, $value1$, "get $type$ value");
1437             }
1438 
1439 
1440             // Volatile
1441             {
1442                 vh.setVolatile(array, i, $value2$);
1443                 $type$ x = ($type$) vh.getVolatile(array, i);
1444                 assertEquals(x, $value2$, "setVolatile $type$ value");
1445             }
1446 
1447             // Lazy
1448             {
1449                 vh.setRelease(array, i, $value1$);
1450                 $type$ x = ($type$) vh.getAcquire(array, i);
1451                 assertEquals(x, $value1$, "setRelease $type$ value");
1452             }
1453 
1454             // Opaque
1455             {
1456                 vh.setOpaque(array, i, $value2$);
1457                 $type$ x = ($type$) vh.getOpaque(array, i);
1458                 assertEquals(x, $value2$, "setOpaque $type$ value");
1459             }
1460 
1461 #if[CAS]
1462             vh.set(array, i, $value1$);
1463 
1464             // Compare
1465             {
1466                 boolean r = vh.compareAndSet(array, i, $value1$, $value2$);
1467                 assertEquals(r, true, "success compareAndSet $type$");
1468                 $type$ x = ($type$) vh.get(array, i);
1469                 assertEquals(x, $value2$, "success compareAndSet $type$ value");
1470             }
1471 
1472             {
1473                 boolean r = vh.compareAndSet(array, i, $value1$, $value3$);
1474                 assertEquals(r, false, "failing compareAndSet $type$");
1475                 $type$ x = ($type$) vh.get(array, i);
1476                 assertEquals(x, $value2$, "failing compareAndSet $type$ value");
1477             }
1478 
1479             {
1480                 $type$ r = ($type$) vh.compareAndExchange(array, i, $value2$, $value1$);
1481                 assertEquals(r, $value2$, "success compareAndExchange $type$");
1482                 $type$ x = ($type$) vh.get(array, i);
1483                 assertEquals(x, $value1$, "success compareAndExchange $type$ value");
1484             }
1485 
1486             {
1487                 $type$ r = ($type$) vh.compareAndExchange(array, i, $value2$, $value3$);
1488                 assertEquals(r, $value1$, "failing compareAndExchange $type$");
1489                 $type$ x = ($type$) vh.get(array, i);
1490                 assertEquals(x, $value1$, "failing compareAndExchange $type$ value");
1491             }
1492 
1493             {
1494                 $type$ r = ($type$) vh.compareAndExchangeAcquire(array, i, $value1$, $value2$);
1495                 assertEquals(r, $value1$, "success compareAndExchangeAcquire $type$");
1496                 $type$ x = ($type$) vh.get(array, i);
1497                 assertEquals(x, $value2$, "success compareAndExchangeAcquire $type$ value");
1498             }
1499 
1500             {
1501                 $type$ r = ($type$) vh.compareAndExchangeAcquire(array, i, $value1$, $value3$);
1502                 assertEquals(r, $value2$, "failing compareAndExchangeAcquire $type$");
1503                 $type$ x = ($type$) vh.get(array, i);
1504                 assertEquals(x, $value2$, "failing compareAndExchangeAcquire $type$ value");
1505             }
1506 
1507             {
1508                 $type$ r = ($type$) vh.compareAndExchangeRelease(array, i, $value2$, $value1$);
1509                 assertEquals(r, $value2$, "success compareAndExchangeRelease $type$");
1510                 $type$ x = ($type$) vh.get(array, i);
1511                 assertEquals(x, $value1$, "success compareAndExchangeRelease $type$ value");
1512             }
1513 
1514             {
1515                 $type$ r = ($type$) vh.compareAndExchangeRelease(array, i, $value2$, $value3$);
1516                 assertEquals(r, $value1$, "failing compareAndExchangeRelease $type$");
1517                 $type$ x = ($type$) vh.get(array, i);
1518                 assertEquals(x, $value1$, "failing compareAndExchangeRelease $type$ value");
1519             }
1520 
1521             {
1522                 boolean success = false;
1523                 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
1524                     success = vh.weakCompareAndSetPlain(array, i, $value1$, $value2$);
1525                 }
1526                 assertEquals(success, true, "weakCompareAndSetPlain $type$");
1527                 $type$ x = ($type$) vh.get(array, i);
1528                 assertEquals(x, $value2$, "weakCompareAndSetPlain $type$ value");
1529             }
1530 
1531             {
1532                 boolean success = false;
1533                 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
1534                     success = vh.weakCompareAndSetAcquire(array, i, $value2$, $value1$);
1535                 }
1536                 assertEquals(success, true, "weakCompareAndSetAcquire $type$");
1537                 $type$ x = ($type$) vh.get(array, i);
1538                 assertEquals(x, $value1$, "weakCompareAndSetAcquire $type$");
1539             }
1540 
1541             {
1542                 boolean success = false;
1543                 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
1544                     success = vh.weakCompareAndSetRelease(array, i, $value1$, $value2$);
1545                 }
1546                 assertEquals(success, true, "weakCompareAndSetRelease $type$");
1547                 $type$ x = ($type$) vh.get(array, i);
1548                 assertEquals(x, $value2$, "weakCompareAndSetRelease $type$");
1549             }
1550 
1551             {
1552                 boolean success = false;
1553                 for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
1554                     success = vh.weakCompareAndSet(array, i, $value2$, $value1$);
1555                 }
1556                 assertEquals(success, true, "weakCompareAndSet $type$");
1557                 $type$ x = ($type$) vh.get(array, i);
1558                 assertEquals(x, $value1$, "weakCompareAndSet $type$");
1559             }
1560 
1561             // Compare set and get
1562             {
1563                 vh.set(array, i, $value1$);
1564 
1565                 $type$ o = ($type$) vh.getAndSet(array, i, $value2$);
1566                 assertEquals(o, $value1$, "getAndSet $type$");
1567                 $type$ x = ($type$) vh.get(array, i);
1568                 assertEquals(x, $value2$, "getAndSet $type$ value");
1569             }
1570 
1571             {
1572                 vh.set(array, i, $value1$);
1573 
1574                 $type$ o = ($type$) vh.getAndSetAcquire(array, i, $value2$);
1575                 assertEquals(o, $value1$, "getAndSetAcquire $type$");
1576                 $type$ x = ($type$) vh.get(array, i);
1577                 assertEquals(x, $value2$, "getAndSetAcquire $type$ value");
1578             }
1579 
1580             {
1581                 vh.set(array, i, $value1$);
1582 
1583                 $type$ o = ($type$) vh.getAndSetRelease(array, i, $value2$);
1584                 assertEquals(o, $value1$, "getAndSetRelease $type$");
1585                 $type$ x = ($type$) vh.get(array, i);
1586                 assertEquals(x, $value2$, "getAndSetRelease $type$ value");
1587             }
1588 #end[CAS]
1589 
1590 #if[AtomicAdd]
1591             // get and add, add and get
1592             {
1593                 vh.set(array, i, $value1$);
1594 
1595                 $type$ o = ($type$) vh.getAndAdd(array, i, $value2$);
1596                 assertEquals(o, $value1$, "getAndAdd $type$");
1597                 $type$ x = ($type$) vh.get(array, i);
1598                 assertEquals(x, ($type$)($value1$ + $value2$), "getAndAdd $type$ value");
1599             }
1600 
1601             {
1602                 vh.set(array, i, $value1$);
1603 
1604                 $type$ o = ($type$) vh.getAndAddAcquire(array, i, $value2$);
1605                 assertEquals(o, $value1$, "getAndAddAcquire $type$");
1606                 $type$ x = ($type$) vh.get(array, i);
1607                 assertEquals(x, ($type$)($value1$ + $value2$), "getAndAddAcquire $type$ value");
1608             }
1609 
1610             {
1611                 vh.set(array, i, $value1$);
1612 
1613                 $type$ o = ($type$) vh.getAndAddRelease(array, i, $value2$);
1614                 assertEquals(o, $value1$, "getAndAddRelease$type$");
1615                 $type$ x = ($type$) vh.get(array, i);
1616                 assertEquals(x, ($type$)($value1$ + $value2$), "getAndAddRelease $type$ value");
1617             }
1618 #end[AtomicAdd]
1619 
1620 #if[Bitwise]
1621             // get and bitwise or
1622             {
1623                 vh.set(array, i, $value1$);
1624 
1625                 $type$ o = ($type$) vh.getAndBitwiseOr(array, i, $value2$);
1626                 assertEquals(o, $value1$, "getAndBitwiseOr $type$");
1627                 $type$ x = ($type$) vh.get(array, i);
1628                 assertEquals(x, ($type$)($value1$ | $value2$), "getAndBitwiseOr $type$ value");
1629             }
1630 
1631             {
1632                 vh.set(array, i, $value1$);
1633 
1634                 $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, i, $value2$);
1635                 assertEquals(o, $value1$, "getAndBitwiseOrAcquire $type$");
1636                 $type$ x = ($type$) vh.get(array, i);
1637                 assertEquals(x, ($type$)($value1$ | $value2$), "getAndBitwiseOrAcquire $type$ value");
1638             }
1639 
1640             {
1641                 vh.set(array, i, $value1$);
1642 
1643                 $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, i, $value2$);
1644                 assertEquals(o, $value1$, "getAndBitwiseOrRelease $type$");
1645                 $type$ x = ($type$) vh.get(array, i);
1646                 assertEquals(x, ($type$)($value1$ | $value2$), "getAndBitwiseOrRelease $type$ value");
1647             }
1648 
1649             // get and bitwise and
1650             {
1651                 vh.set(array, i, $value1$);
1652 
1653                 $type$ o = ($type$) vh.getAndBitwiseAnd(array, i, $value2$);
1654                 assertEquals(o, $value1$, "getAndBitwiseAnd $type$");
1655                 $type$ x = ($type$) vh.get(array, i);
1656                 assertEquals(x, ($type$)($value1$ & $value2$), "getAndBitwiseAnd $type$ value");
1657             }
1658 
1659             {
1660                 vh.set(array, i, $value1$);
1661 
1662                 $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, i, $value2$);
1663                 assertEquals(o, $value1$, "getAndBitwiseAndAcquire $type$");
1664                 $type$ x = ($type$) vh.get(array, i);
1665                 assertEquals(x, ($type$)($value1$ & $value2$), "getAndBitwiseAndAcquire $type$ value");
1666             }
1667 
1668             {
1669                 vh.set(array, i, $value1$);
1670 
1671                 $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, i, $value2$);
1672                 assertEquals(o, $value1$, "getAndBitwiseAndRelease $type$");
1673                 $type$ x = ($type$) vh.get(array, i);
1674                 assertEquals(x, ($type$)($value1$ & $value2$), "getAndBitwiseAndRelease $type$ value");
1675             }
1676 
1677             // get and bitwise xor
1678             {
1679                 vh.set(array, i, $value1$);
1680 
1681                 $type$ o = ($type$) vh.getAndBitwiseXor(array, i, $value2$);
1682                 assertEquals(o, $value1$, "getAndBitwiseXor $type$");
1683                 $type$ x = ($type$) vh.get(array, i);
1684                 assertEquals(x, ($type$)($value1$ ^ $value2$), "getAndBitwiseXor $type$ value");
1685             }
1686 
1687             {
1688                 vh.set(array, i, $value1$);
1689 
1690                 $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, i, $value2$);
1691                 assertEquals(o, $value1$, "getAndBitwiseXorAcquire $type$");
1692                 $type$ x = ($type$) vh.get(array, i);
1693                 assertEquals(x, ($type$)($value1$ ^ $value2$), "getAndBitwiseXorAcquire $type$ value");
1694             }
1695 
1696             {
1697                 vh.set(array, i, $value1$);
1698 
1699                 $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, i, $value2$);
1700                 assertEquals(o, $value1$, "getAndBitwiseXorRelease $type$");
1701                 $type$ x = ($type$) vh.get(array, i);
1702                 assertEquals(x, ($type$)($value1$ ^ $value2$), "getAndBitwiseXorRelease $type$ value");
1703             }
1704 #end[Bitwise]
1705         }
1706     }
1707 
1708     static void testArrayUnsupported(VarHandle vh) {
1709         $type$[] array = new $type$[10];
1710 
1711         int i = 0;
1712 #if[!CAS]
1713         checkUOE(() -> {
1714             boolean r = vh.compareAndSet(array, i, $value1$, $value2$);
1715         });
1716 
1717         checkUOE(() -> {
1718             $type$ r = ($type$) vh.compareAndExchange(array, i, $value1$, $value2$);
1719         });
1720 
1721         checkUOE(() -> {
1722             $type$ r = ($type$) vh.compareAndExchangeAcquire(array, i, $value1$, $value2$);
1723         });
1724 
1725         checkUOE(() -> {
1726             $type$ r = ($type$) vh.compareAndExchangeRelease(array, i, $value1$, $value2$);
1727         });
1728 
1729         checkUOE(() -> {
1730             boolean r = vh.weakCompareAndSetPlain(array, i, $value1$, $value2$);
1731         });
1732 
1733         checkUOE(() -> {
1734             boolean r = vh.weakCompareAndSet(array, i, $value1$, $value2$);
1735         });
1736 
1737         checkUOE(() -> {
1738             boolean r = vh.weakCompareAndSetAcquire(array, i, $value1$, $value2$);
1739         });
1740 
1741         checkUOE(() -> {
1742             boolean r = vh.weakCompareAndSetRelease(array, i, $value1$, $value2$);
1743         });
1744 
1745         checkUOE(() -> {
1746             $type$ r = ($type$) vh.getAndSet(array, i, $value1$);
1747         });
1748 
1749         checkUOE(() -> {
1750             $type$ r = ($type$) vh.getAndSetAcquire(array, i, $value1$);
1751         });
1752 
1753         checkUOE(() -> {
1754             $type$ r = ($type$) vh.getAndSetRelease(array, i, $value1$);
1755         });
1756 #end[CAS]
1757 
1758 #if[!AtomicAdd]
1759         checkUOE(() -> {
1760             $type$ o = ($type$) vh.getAndAdd(array, i, $value1$);
1761         });
1762 
1763         checkUOE(() -> {
1764             $type$ o = ($type$) vh.getAndAddAcquire(array, i, $value1$);
1765         });
1766 
1767         checkUOE(() -> {
1768             $type$ o = ($type$) vh.getAndAddRelease(array, i, $value1$);
1769         });
1770 #end[AtomicAdd]
1771 
1772 #if[!Bitwise]
1773         checkUOE(() -> {
1774             $type$ o = ($type$) vh.getAndBitwiseOr(array, i, $value1$);
1775         });
1776 
1777         checkUOE(() -> {
1778             $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, i, $value1$);
1779         });
1780 
1781         checkUOE(() -> {
1782             $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, i, $value1$);
1783         });
1784 
1785         checkUOE(() -> {
1786             $type$ o = ($type$) vh.getAndBitwiseAnd(array, i, $value1$);
1787         });
1788 
1789         checkUOE(() -> {
1790             $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, i, $value1$);
1791         });
1792 
1793         checkUOE(() -> {
1794             $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, i, $value1$);
1795         });
1796 
1797         checkUOE(() -> {
1798             $type$ o = ($type$) vh.getAndBitwiseXor(array, i, $value1$);
1799         });
1800 
1801         checkUOE(() -> {
1802             $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, i, $value1$);
1803         });
1804 
1805         checkUOE(() -> {
1806             $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, i, $value1$);
1807         });
1808 #end[Bitwise]
1809     }
1810 
1811     static void testArrayIndexOutOfBounds(VarHandle vh) throws Throwable {
1812         $type$[] array = new $type$[10];
1813 
1814         for (int i : new int[]{-1, Integer.MIN_VALUE, 10, 11, Integer.MAX_VALUE}) {
1815             final int ci = i;
1816 
1817             checkIOOBE(() -> {
1818                 $type$ x = ($type$) vh.get(array, ci);
1819             });
1820 
1821             checkIOOBE(() -> {
1822                 vh.set(array, ci, $value1$);
1823             });
1824 
1825             checkIOOBE(() -> {
1826                 $type$ x = ($type$) vh.getVolatile(array, ci);
1827             });
1828 
1829             checkIOOBE(() -> {
1830                 vh.setVolatile(array, ci, $value1$);
1831             });
1832 
1833             checkIOOBE(() -> {
1834                 $type$ x = ($type$) vh.getAcquire(array, ci);
1835             });
1836 
1837             checkIOOBE(() -> {
1838                 vh.setRelease(array, ci, $value1$);
1839             });
1840 
1841             checkIOOBE(() -> {
1842                 $type$ x = ($type$) vh.getOpaque(array, ci);
1843             });
1844 
1845             checkIOOBE(() -> {
1846                 vh.setOpaque(array, ci, $value1$);
1847             });
1848 
1849 #if[CAS]
1850             checkIOOBE(() -> {
1851                 boolean r = vh.compareAndSet(array, ci, $value1$, $value2$);
1852             });
1853 
1854             checkIOOBE(() -> {
1855                 $type$ r = ($type$) vh.compareAndExchange(array, ci, $value2$, $value1$);
1856             });
1857 
1858             checkIOOBE(() -> {
1859                 $type$ r = ($type$) vh.compareAndExchangeAcquire(array, ci, $value2$, $value1$);
1860             });
1861 
1862             checkIOOBE(() -> {
1863                 $type$ r = ($type$) vh.compareAndExchangeRelease(array, ci, $value2$, $value1$);
1864             });
1865 
1866             checkIOOBE(() -> {
1867                 boolean r = vh.weakCompareAndSetPlain(array, ci, $value1$, $value2$);
1868             });
1869 
1870             checkIOOBE(() -> {
1871                 boolean r = vh.weakCompareAndSet(array, ci, $value1$, $value2$);
1872             });
1873 
1874             checkIOOBE(() -> {
1875                 boolean r = vh.weakCompareAndSetAcquire(array, ci, $value1$, $value2$);
1876             });
1877 
1878             checkIOOBE(() -> {
1879                 boolean r = vh.weakCompareAndSetRelease(array, ci, $value1$, $value2$);
1880             });
1881 
1882             checkIOOBE(() -> {
1883                 $type$ o = ($type$) vh.getAndSet(array, ci, $value1$);
1884             });
1885 
1886             checkIOOBE(() -> {
1887                 $type$ o = ($type$) vh.getAndSetAcquire(array, ci, $value1$);
1888             });
1889 
1890             checkIOOBE(() -> {
1891                 $type$ o = ($type$) vh.getAndSetRelease(array, ci, $value1$);
1892             });
1893 #end[CAS]
1894 
1895 #if[AtomicAdd]
1896             checkIOOBE(() -> {
1897                 $type$ o = ($type$) vh.getAndAdd(array, ci, $value1$);
1898             });
1899 
1900             checkIOOBE(() -> {
1901                 $type$ o = ($type$) vh.getAndAddAcquire(array, ci, $value1$);
1902             });
1903 
1904             checkIOOBE(() -> {
1905                 $type$ o = ($type$) vh.getAndAddRelease(array, ci, $value1$);
1906             });
1907 #end[AtomicAdd]
1908 
1909 #if[Bitwise]
1910             checkIOOBE(() -> {
1911                 $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, $value1$);
1912             });
1913 
1914             checkIOOBE(() -> {
1915                 $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, ci, $value1$);
1916             });
1917 
1918             checkIOOBE(() -> {
1919                 $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, ci, $value1$);
1920             });
1921 
1922             checkIOOBE(() -> {
1923                 $type$ o = ($type$) vh.getAndBitwiseAnd(array, ci, $value1$);
1924             });
1925 
1926             checkIOOBE(() -> {
1927                 $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, ci, $value1$);
1928             });
1929 
1930             checkIOOBE(() -> {
1931                 $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, ci, $value1$);
1932             });
1933 
1934             checkIOOBE(() -> {
1935                 $type$ o = ($type$) vh.getAndBitwiseXor(array, ci, $value1$);
1936             });
1937 
1938             checkIOOBE(() -> {
1939                 $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, ci, $value1$);
1940             });
1941 
1942             checkIOOBE(() -> {
1943                 $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, $value1$);
1944             });
1945 #end[Bitwise]
1946         }
1947     }
1948 
1949 #if[String]
1950     static void testArrayStoreException(VarHandle vh) throws Throwable {
1951         Object[] array = new $type$[10];
1952         Arrays.fill(array, $value1$);
1953         Object value = new Object();
1954 
1955         // Set
1956         checkASE(() -> {
1957             vh.set(array, 0, value);
1958         });
1959 
1960         // SetVolatile
1961         checkASE(() -> {
1962             vh.setVolatile(array, 0, value);
1963         });
1964 
1965         // SetOpaque
1966         checkASE(() -> {
1967             vh.setOpaque(array, 0, value);
1968         });
1969 
1970         // SetRelease
1971         checkASE(() -> {
1972             vh.setRelease(array, 0, value);
1973         });
1974 
1975         // CompareAndSet
1976         checkASE(() -> { // receiver reference class
1977             boolean r = vh.compareAndSet(array, 0, $value1$, value);
1978         });
1979 
1980         // WeakCompareAndSet
1981         checkASE(() -> { // receiver reference class
1982             boolean r = vh.weakCompareAndSetPlain(array, 0, $value1$, value);
1983         });
1984 
1985         // WeakCompareAndSetVolatile
1986         checkASE(() -> { // receiver reference class
1987             boolean r = vh.weakCompareAndSet(array, 0, $value1$, value);
1988         });
1989 
1990         // WeakCompareAndSetAcquire
1991         checkASE(() -> { // receiver reference class
1992             boolean r = vh.weakCompareAndSetAcquire(array, 0, $value1$, value);
1993         });
1994 
1995         // WeakCompareAndSetRelease
1996         checkASE(() -> { // receiver reference class
1997             boolean r = vh.weakCompareAndSetRelease(array, 0, $value1$, value);
1998         });
1999 
2000         // CompareAndExchange
2001         checkASE(() -> { // receiver reference class
2002             $type$ x = ($type$) vh.compareAndExchange(array, 0, $value1$, value);
2003         });
2004 
2005         // CompareAndExchangeAcquire
2006         checkASE(() -> { // receiver reference class
2007             $type$ x = ($type$) vh.compareAndExchangeAcquire(array, 0, $value1$, value);
2008         });
2009 
2010         // CompareAndExchangeRelease
2011         checkASE(() -> { // receiver reference class
2012             $type$ x = ($type$) vh.compareAndExchangeRelease(array, 0, $value1$, value);
2013         });
2014 
2015         // GetAndSet
2016         checkASE(() -> { // receiver reference class
2017             $type$ x = ($type$) vh.getAndSet(array, 0, value);
2018         });
2019 
2020         // GetAndSetAcquire
2021         checkASE(() -> { // receiver reference class
2022             $type$ x = ($type$) vh.getAndSetAcquire(array, 0, value);
2023         });
2024 
2025         // GetAndSetRelease
2026         checkASE(() -> { // receiver reference class
2027             $type$ x = ($type$) vh.getAndSetRelease(array, 0, value);
2028         });
2029     }
2030 #end[String]
2031 }
2032