1/*
2 * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 */
23
24/*
25 * @test
26 * @run testng/othervm -Diters=20000 VarHandleTestMethodHandleAccessString
27 */
28
29import org.testng.annotations.BeforeClass;
30import org.testng.annotations.DataProvider;
31import org.testng.annotations.Test;
32
33import java.lang.invoke.MethodHandles;
34import java.lang.invoke.VarHandle;
35import java.util.ArrayList;
36import java.util.Arrays;
37import java.util.List;
38
39import static org.testng.Assert.*;
40
41public class VarHandleTestMethodHandleAccessString extends VarHandleBaseTest {
42    static final String static_final_v = "foo";
43
44    static String static_v;
45
46    final String final_v = "foo";
47
48    String v;
49
50    VarHandle vhFinalField;
51
52    VarHandle vhField;
53
54    VarHandle vhStaticField;
55
56    VarHandle vhStaticFinalField;
57
58    VarHandle vhArray;
59
60    @BeforeClass
61    public void setup() throws Exception {
62        vhFinalField = MethodHandles.lookup().findVarHandle(
63                VarHandleTestMethodHandleAccessString.class, "final_v", String.class);
64
65        vhField = MethodHandles.lookup().findVarHandle(
66                VarHandleTestMethodHandleAccessString.class, "v", String.class);
67
68        vhStaticFinalField = MethodHandles.lookup().findStaticVarHandle(
69            VarHandleTestMethodHandleAccessString.class, "static_final_v", String.class);
70
71        vhStaticField = MethodHandles.lookup().findStaticVarHandle(
72            VarHandleTestMethodHandleAccessString.class, "static_v", String.class);
73
74        vhArray = MethodHandles.arrayElementVarHandle(String[].class);
75    }
76
77
78    @DataProvider
79    public Object[][] accessTestCaseProvider() throws Exception {
80        List<AccessTestCase<?>> cases = new ArrayList<>();
81
82        for (VarHandleToMethodHandle f : VarHandleToMethodHandle.values()) {
83            cases.add(new MethodHandleAccessTestCase("Instance field",
84                                                     vhField, f, hs -> testInstanceField(this, hs)));
85            cases.add(new MethodHandleAccessTestCase("Instance field unsupported",
86                                                     vhField, f, hs -> testInstanceFieldUnsupported(this, hs),
87                                                     false));
88
89            cases.add(new MethodHandleAccessTestCase("Static field",
90                                                     vhStaticField, f, VarHandleTestMethodHandleAccessString::testStaticField));
91            cases.add(new MethodHandleAccessTestCase("Static field unsupported",
92                                                     vhStaticField, f, VarHandleTestMethodHandleAccessString::testStaticFieldUnsupported,
93                                                     false));
94
95            cases.add(new MethodHandleAccessTestCase("Array",
96                                                     vhArray, f, VarHandleTestMethodHandleAccessString::testArray));
97            cases.add(new MethodHandleAccessTestCase("Array unsupported",
98                                                     vhArray, f, VarHandleTestMethodHandleAccessString::testArrayUnsupported,
99                                                     false));
100            cases.add(new MethodHandleAccessTestCase("Array index out of bounds",
101                                                     vhArray, f, VarHandleTestMethodHandleAccessString::testArrayIndexOutOfBounds,
102                                                     false));
103        }
104
105        // Work around issue with jtreg summary reporting which truncates
106        // the String result of Object.toString to 30 characters, hence
107        // the first dummy argument
108        return cases.stream().map(tc -> new Object[]{tc.toString(), tc}).toArray(Object[][]::new);
109    }
110
111    @Test(dataProvider = "accessTestCaseProvider")
112    public <T> void testAccess(String desc, AccessTestCase<T> atc) throws Throwable {
113        T t = atc.get();
114        int iters = atc.requiresLoop() ? ITERS : 1;
115        for (int c = 0; c < iters; c++) {
116            atc.testAccess(t);
117        }
118    }
119
120
121    static void testInstanceField(VarHandleTestMethodHandleAccessString recv, Handles hs) throws Throwable {
122        // Plain
123        {
124            hs.get(TestAccessMode.SET).invokeExact(recv, "foo");
125            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
126            assertEquals(x, "foo", "set String value");
127        }
128
129
130        // Volatile
131        {
132            hs.get(TestAccessMode.SET_VOLATILE).invokeExact(recv, "bar");
133            String x = (String) hs.get(TestAccessMode.GET_VOLATILE).invokeExact(recv);
134            assertEquals(x, "bar", "setVolatile String value");
135        }
136
137        // Lazy
138        {
139            hs.get(TestAccessMode.SET_RELEASE).invokeExact(recv, "foo");
140            String x = (String) hs.get(TestAccessMode.GET_ACQUIRE).invokeExact(recv);
141            assertEquals(x, "foo", "setRelease String value");
142        }
143
144        // Opaque
145        {
146            hs.get(TestAccessMode.SET_OPAQUE).invokeExact(recv, "bar");
147            String x = (String) hs.get(TestAccessMode.GET_OPAQUE).invokeExact(recv);
148            assertEquals(x, "bar", "setOpaque String value");
149        }
150
151        hs.get(TestAccessMode.SET).invokeExact(recv, "foo");
152
153        // Compare
154        {
155            boolean r = (boolean) hs.get(TestAccessMode.COMPARE_AND_SET).invokeExact(recv, "foo", "bar");
156            assertEquals(r, true, "success compareAndSet String");
157            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
158            assertEquals(x, "bar", "success compareAndSet String value");
159        }
160
161        {
162            boolean r = (boolean) hs.get(TestAccessMode.COMPARE_AND_SET).invokeExact(recv, "foo", "baz");
163            assertEquals(r, false, "failing compareAndSet String");
164            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
165            assertEquals(x, "bar", "failing compareAndSet String value");
166        }
167
168        {
169            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE).invokeExact(recv, "bar", "foo");
170            assertEquals(r, "bar", "success compareAndExchange String");
171            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
172            assertEquals(x, "foo", "success compareAndExchange String value");
173        }
174
175        {
176            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE).invokeExact(recv, "bar", "baz");
177            assertEquals(r, "foo", "failing compareAndExchange String");
178            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
179            assertEquals(x, "foo", "failing compareAndExchange String value");
180        }
181
182        {
183            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_ACQUIRE).invokeExact(recv, "foo", "bar");
184            assertEquals(r, "foo", "success compareAndExchangeAcquire String");
185            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
186            assertEquals(x, "bar", "success compareAndExchangeAcquire String value");
187        }
188
189        {
190            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_ACQUIRE).invokeExact(recv, "foo", "baz");
191            assertEquals(r, "bar", "failing compareAndExchangeAcquire String");
192            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
193            assertEquals(x, "bar", "failing compareAndExchangeAcquire String value");
194        }
195
196        {
197            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_RELEASE).invokeExact(recv, "bar", "foo");
198            assertEquals(r, "bar", "success compareAndExchangeRelease String");
199            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
200            assertEquals(x, "foo", "success compareAndExchangeRelease String value");
201        }
202
203        {
204            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_RELEASE).invokeExact(recv, "bar", "baz");
205            assertEquals(r, "foo", "failing compareAndExchangeRelease String");
206            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
207            assertEquals(x, "foo", "failing compareAndExchangeRelease String value");
208        }
209
210        {
211            boolean success = false;
212            for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
213                success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET_PLAIN).invokeExact(recv, "foo", "bar");
214            }
215            assertEquals(success, true, "weakCompareAndSetPlain String");
216            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
217            assertEquals(x, "bar", "weakCompareAndSetPlain String value");
218        }
219
220        {
221            boolean success = false;
222            for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
223                success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET_ACQUIRE).invokeExact(recv, "bar", "foo");
224            }
225            assertEquals(success, true, "weakCompareAndSetAcquire String");
226            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
227            assertEquals(x, "foo", "weakCompareAndSetAcquire String");
228        }
229
230        {
231            boolean success = false;
232            for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
233                success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET_RELEASE).invokeExact(recv, "foo", "bar");
234            }
235            assertEquals(success, true, "weakCompareAndSetRelease String");
236            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
237            assertEquals(x, "bar", "weakCompareAndSetRelease String");
238        }
239
240        {
241            boolean success = false;
242            for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
243                success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET).invokeExact(recv, "bar", "foo");
244            }
245            assertEquals(success, true, "weakCompareAndSet String");
246            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
247            assertEquals(x, "foo", "weakCompareAndSet String");
248        }
249
250        // Compare set and get
251        {
252            String o = (String) hs.get(TestAccessMode.GET_AND_SET).invokeExact(recv, "bar");
253            assertEquals(o, "foo", "getAndSet String");
254            String x = (String) hs.get(TestAccessMode.GET).invokeExact(recv);
255            assertEquals(x, "bar", "getAndSet String value");
256        }
257
258
259    }
260
261    static void testInstanceFieldUnsupported(VarHandleTestMethodHandleAccessString recv, Handles hs) throws Throwable {
262
263        for (TestAccessMode am : testAccessModesOfType(TestAccessType.GET_AND_ADD)) {
264            checkUOE(am, () -> {
265                String r = (String) hs.get(am).invokeExact(recv, "foo");
266            });
267        }
268
269        for (TestAccessMode am : testAccessModesOfType(TestAccessType.GET_AND_BITWISE)) {
270            checkUOE(am, () -> {
271                String r = (String) hs.get(am).invokeExact(recv, "foo");
272            });
273        }
274    }
275
276
277    static void testStaticField(Handles hs) throws Throwable {
278        // Plain
279        {
280            hs.get(TestAccessMode.SET).invokeExact("foo");
281            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
282            assertEquals(x, "foo", "set String value");
283        }
284
285
286        // Volatile
287        {
288            hs.get(TestAccessMode.SET_VOLATILE).invokeExact("bar");
289            String x = (String) hs.get(TestAccessMode.GET_VOLATILE).invokeExact();
290            assertEquals(x, "bar", "setVolatile String value");
291        }
292
293        // Lazy
294        {
295            hs.get(TestAccessMode.SET_RELEASE).invokeExact("foo");
296            String x = (String) hs.get(TestAccessMode.GET_ACQUIRE).invokeExact();
297            assertEquals(x, "foo", "setRelease String value");
298        }
299
300        // Opaque
301        {
302            hs.get(TestAccessMode.SET_OPAQUE).invokeExact("bar");
303            String x = (String) hs.get(TestAccessMode.GET_OPAQUE).invokeExact();
304            assertEquals(x, "bar", "setOpaque String value");
305        }
306
307        hs.get(TestAccessMode.SET).invokeExact("foo");
308
309        // Compare
310        {
311            boolean r = (boolean) hs.get(TestAccessMode.COMPARE_AND_SET).invokeExact("foo", "bar");
312            assertEquals(r, true, "success compareAndSet String");
313            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
314            assertEquals(x, "bar", "success compareAndSet String value");
315        }
316
317        {
318            boolean r = (boolean) hs.get(TestAccessMode.COMPARE_AND_SET).invokeExact("foo", "baz");
319            assertEquals(r, false, "failing compareAndSet String");
320            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
321            assertEquals(x, "bar", "failing compareAndSet String value");
322        }
323
324        {
325            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE).invokeExact("bar", "foo");
326            assertEquals(r, "bar", "success compareAndExchange String");
327            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
328            assertEquals(x, "foo", "success compareAndExchange String value");
329        }
330
331        {
332            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE).invokeExact("bar", "baz");
333            assertEquals(r, "foo", "failing compareAndExchange String");
334            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
335            assertEquals(x, "foo", "failing compareAndExchange String value");
336        }
337
338        {
339            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_ACQUIRE).invokeExact("foo", "bar");
340            assertEquals(r, "foo", "success compareAndExchangeAcquire String");
341            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
342            assertEquals(x, "bar", "success compareAndExchangeAcquire String value");
343        }
344
345        {
346            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_ACQUIRE).invokeExact("foo", "baz");
347            assertEquals(r, "bar", "failing compareAndExchangeAcquire String");
348            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
349            assertEquals(x, "bar", "failing compareAndExchangeAcquire String value");
350        }
351
352        {
353            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_RELEASE).invokeExact("bar", "foo");
354            assertEquals(r, "bar", "success compareAndExchangeRelease String");
355            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
356            assertEquals(x, "foo", "success compareAndExchangeRelease String value");
357        }
358
359        {
360            String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_RELEASE).invokeExact("bar", "baz");
361            assertEquals(r, "foo", "failing compareAndExchangeRelease String");
362            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
363            assertEquals(x, "foo", "failing compareAndExchangeRelease String value");
364        }
365
366        {
367            boolean success = false;
368            for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
369                success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET_PLAIN).invokeExact("foo", "bar");
370            }
371            assertEquals(success, true, "weakCompareAndSetPlain String");
372            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
373            assertEquals(x, "bar", "weakCompareAndSetPlain String value");
374        }
375
376        {
377            boolean success = false;
378            for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
379                success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET_ACQUIRE).invokeExact("bar", "foo");
380            }
381            assertEquals(success, true, "weakCompareAndSetAcquire String");
382            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
383            assertEquals(x, "foo", "weakCompareAndSetAcquire String");
384        }
385
386        {
387            boolean success = false;
388            for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
389                success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET_RELEASE).invokeExact("foo", "bar");
390            }
391            assertEquals(success, true, "weakCompareAndSetRelease String");
392            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
393            assertEquals(x, "bar", "weakCompareAndSetRelease String");
394        }
395
396        {
397            boolean success = false;
398            for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
399                success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET).invokeExact("bar", "foo");
400            }
401            assertEquals(success, true, "weakCompareAndSet String");
402            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
403            assertEquals(x, "foo", "weakCompareAndSet String");
404        }
405
406        // Compare set and get
407        {
408            hs.get(TestAccessMode.SET).invokeExact("foo");
409
410            String o = (String) hs.get(TestAccessMode.GET_AND_SET).invokeExact("bar");
411            assertEquals(o, "foo", "getAndSet String");
412            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
413            assertEquals(x, "bar", "getAndSet String value");
414        }
415
416        // Compare set and get
417        {
418            hs.get(TestAccessMode.SET).invokeExact("foo");
419
420            String o = (String) hs.get(TestAccessMode.GET_AND_SET_ACQUIRE).invokeExact("bar");
421            assertEquals(o, "foo", "getAndSetAcquire String");
422            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
423            assertEquals(x, "bar", "getAndSetAcquire String value");
424        }
425
426        // Compare set and get
427        {
428            hs.get(TestAccessMode.SET).invokeExact("foo");
429
430            String o = (String) hs.get(TestAccessMode.GET_AND_SET_RELEASE).invokeExact("bar");
431            assertEquals(o, "foo", "getAndSetRelease String");
432            String x = (String) hs.get(TestAccessMode.GET).invokeExact();
433            assertEquals(x, "bar", "getAndSetRelease String value");
434        }
435
436
437    }
438
439    static void testStaticFieldUnsupported(Handles hs) throws Throwable {
440
441        for (TestAccessMode am : testAccessModesOfType(TestAccessType.GET_AND_ADD)) {
442            checkUOE(am, () -> {
443                String r = (String) hs.get(am).invokeExact("foo");
444            });
445        }
446
447        for (TestAccessMode am : testAccessModesOfType(TestAccessType.GET_AND_BITWISE)) {
448            checkUOE(am, () -> {
449                String r = (String) hs.get(am).invokeExact("foo");
450            });
451        }
452    }
453
454
455    static void testArray(Handles hs) throws Throwable {
456        String[] array = new String[10];
457
458        for (int i = 0; i < array.length; i++) {
459            // Plain
460            {
461                hs.get(TestAccessMode.SET).invokeExact(array, i, "foo");
462                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
463                assertEquals(x, "foo", "get String value");
464            }
465
466
467            // Volatile
468            {
469                hs.get(TestAccessMode.SET_VOLATILE).invokeExact(array, i, "bar");
470                String x = (String) hs.get(TestAccessMode.GET_VOLATILE).invokeExact(array, i);
471                assertEquals(x, "bar", "setVolatile String value");
472            }
473
474            // Lazy
475            {
476                hs.get(TestAccessMode.SET_RELEASE).invokeExact(array, i, "foo");
477                String x = (String) hs.get(TestAccessMode.GET_ACQUIRE).invokeExact(array, i);
478                assertEquals(x, "foo", "setRelease String value");
479            }
480
481            // Opaque
482            {
483                hs.get(TestAccessMode.SET_OPAQUE).invokeExact(array, i, "bar");
484                String x = (String) hs.get(TestAccessMode.GET_OPAQUE).invokeExact(array, i);
485                assertEquals(x, "bar", "setOpaque String value");
486            }
487
488            hs.get(TestAccessMode.SET).invokeExact(array, i, "foo");
489
490            // Compare
491            {
492                boolean r = (boolean) hs.get(TestAccessMode.COMPARE_AND_SET).invokeExact(array, i, "foo", "bar");
493                assertEquals(r, true, "success compareAndSet String");
494                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
495                assertEquals(x, "bar", "success compareAndSet String value");
496            }
497
498            {
499                boolean r = (boolean) hs.get(TestAccessMode.COMPARE_AND_SET).invokeExact(array, i, "foo", "baz");
500                assertEquals(r, false, "failing compareAndSet String");
501                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
502                assertEquals(x, "bar", "failing compareAndSet String value");
503            }
504
505            {
506                String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE).invokeExact(array, i, "bar", "foo");
507                assertEquals(r, "bar", "success compareAndExchange String");
508                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
509                assertEquals(x, "foo", "success compareAndExchange String value");
510            }
511
512            {
513                String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE).invokeExact(array, i, "bar", "baz");
514                assertEquals(r, "foo", "failing compareAndExchange String");
515                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
516                assertEquals(x, "foo", "failing compareAndExchange String value");
517            }
518
519            {
520                String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_ACQUIRE).invokeExact(array, i, "foo", "bar");
521                assertEquals(r, "foo", "success compareAndExchangeAcquire String");
522                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
523                assertEquals(x, "bar", "success compareAndExchangeAcquire String value");
524            }
525
526            {
527                String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_ACQUIRE).invokeExact(array, i, "foo", "baz");
528                assertEquals(r, "bar", "failing compareAndExchangeAcquire String");
529                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
530                assertEquals(x, "bar", "failing compareAndExchangeAcquire String value");
531            }
532
533            {
534                String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_RELEASE).invokeExact(array, i, "bar", "foo");
535                assertEquals(r, "bar", "success compareAndExchangeRelease String");
536                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
537                assertEquals(x, "foo", "success compareAndExchangeRelease String value");
538            }
539
540            {
541                String r = (String) hs.get(TestAccessMode.COMPARE_AND_EXCHANGE_RELEASE).invokeExact(array, i, "bar", "baz");
542                assertEquals(r, "foo", "failing compareAndExchangeRelease String");
543                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
544                assertEquals(x, "foo", "failing compareAndExchangeRelease String value");
545            }
546
547            {
548                boolean success = false;
549                for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
550                    success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET_PLAIN).invokeExact(array, i, "foo", "bar");
551                }
552                assertEquals(success, true, "weakCompareAndSetPlain String");
553                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
554                assertEquals(x, "bar", "weakCompareAndSetPlain String value");
555            }
556
557            {
558                boolean success = false;
559                for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
560                    success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET_ACQUIRE).invokeExact(array, i, "bar", "foo");
561                }
562                assertEquals(success, true, "weakCompareAndSetAcquire String");
563                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
564                assertEquals(x, "foo", "weakCompareAndSetAcquire String");
565            }
566
567            {
568                boolean success = false;
569                for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
570                    success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET_RELEASE).invokeExact(array, i, "foo", "bar");
571                }
572                assertEquals(success, true, "weakCompareAndSetRelease String");
573                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
574                assertEquals(x, "bar", "weakCompareAndSetRelease String");
575            }
576
577            {
578                boolean success = false;
579                for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) {
580                    success = (boolean) hs.get(TestAccessMode.WEAK_COMPARE_AND_SET).invokeExact(array, i, "bar", "foo");
581                }
582                assertEquals(success, true, "weakCompareAndSet String");
583                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
584                assertEquals(x, "foo", "weakCompareAndSet String");
585            }
586
587            // Compare set and get
588            {
589                hs.get(TestAccessMode.SET).invokeExact(array, i, "foo");
590
591                String o = (String) hs.get(TestAccessMode.GET_AND_SET).invokeExact(array, i, "bar");
592                assertEquals(o, "foo", "getAndSet String");
593                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
594                assertEquals(x, "bar", "getAndSet String value");
595            }
596
597            {
598                hs.get(TestAccessMode.SET).invokeExact(array, i, "foo");
599
600                String o = (String) hs.get(TestAccessMode.GET_AND_SET_ACQUIRE).invokeExact(array, i, "bar");
601                assertEquals(o, "foo", "getAndSetAcquire String");
602                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
603                assertEquals(x, "bar", "getAndSetAcquire String value");
604            }
605
606            {
607                hs.get(TestAccessMode.SET).invokeExact(array, i, "foo");
608
609                String o = (String) hs.get(TestAccessMode.GET_AND_SET_RELEASE).invokeExact(array, i, "bar");
610                assertEquals(o, "foo", "getAndSetRelease String");
611                String x = (String) hs.get(TestAccessMode.GET).invokeExact(array, i);
612                assertEquals(x, "bar", "getAndSetRelease String value");
613            }
614
615
616        }
617    }
618
619    static void testArrayUnsupported(Handles hs) throws Throwable {
620        String[] array = new String[10];
621
622        final int i = 0;
623
624        for (TestAccessMode am : testAccessModesOfType(TestAccessType.GET_AND_ADD)) {
625            checkUOE(am, () -> {
626                String o = (String) hs.get(am).invokeExact(array, i, "foo");
627            });
628        }
629
630        for (TestAccessMode am : testAccessModesOfType(TestAccessType.GET_AND_BITWISE)) {
631            checkUOE(am, () -> {
632                String o = (String) hs.get(am).invokeExact(array, i, "foo");
633            });
634        }
635    }
636
637    static void testArrayIndexOutOfBounds(Handles hs) throws Throwable {
638        String[] array = new String[10];
639
640        for (int i : new int[]{-1, Integer.MIN_VALUE, 10, 11, Integer.MAX_VALUE}) {
641            final int ci = i;
642
643            for (TestAccessMode am : testAccessModesOfType(TestAccessType.GET)) {
644                checkIOOBE(am, () -> {
645                    String x = (String) hs.get(am).invokeExact(array, ci);
646                });
647            }
648
649            for (TestAccessMode am : testAccessModesOfType(TestAccessType.SET)) {
650                checkIOOBE(am, () -> {
651                    hs.get(am).invokeExact(array, ci, "foo");
652                });
653            }
654
655            for (TestAccessMode am : testAccessModesOfType(TestAccessType.COMPARE_AND_SET)) {
656                checkIOOBE(am, () -> {
657                    boolean r = (boolean) hs.get(am).invokeExact(array, ci, "foo", "bar");
658                });
659            }
660
661            for (TestAccessMode am : testAccessModesOfType(TestAccessType.COMPARE_AND_EXCHANGE)) {
662                checkIOOBE(am, () -> {
663                    String r = (String) hs.get(am).invokeExact(array, ci, "bar", "foo");
664                });
665            }
666
667            for (TestAccessMode am : testAccessModesOfType(TestAccessType.GET_AND_SET)) {
668                checkIOOBE(am, () -> {
669                    String o = (String) hs.get(am).invokeExact(array, ci, "foo");
670                });
671            }
672
673
674        }
675    }
676}
677
678