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