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