1/*
2 * Written by Doug Lea with assistance from members of JCP JSR-166
3 * Expert Group and released to the public domain, as explained at
4 * http://creativecommons.org/publicdomain/zero/1.0/
5 * Other contributors include Andrew Wright, Jeffrey Hayes,
6 * Pat Fisher, Mike Judd.
7 */
8
9package jsr166;
10
11import junit.framework.*;
12import java.util.concurrent.atomic.AtomicReference;
13
14public class AtomicReferenceTest extends JSR166TestCase {
15
16    /**
17     * constructor initializes to given value
18     */
19    public void testConstructor() {
20        AtomicReference ai = new AtomicReference(one);
21        assertSame(one, ai.get());
22    }
23
24    /**
25     * default constructed initializes to null
26     */
27    public void testConstructor2() {
28        AtomicReference ai = new AtomicReference();
29        assertNull(ai.get());
30    }
31
32    /**
33     * get returns the last value set
34     */
35    public void testGetSet() {
36        AtomicReference ai = new AtomicReference(one);
37        assertSame(one, ai.get());
38        ai.set(two);
39        assertSame(two, ai.get());
40        ai.set(m3);
41        assertSame(m3, ai.get());
42    }
43
44    /**
45     * get returns the last value lazySet in same thread
46     */
47    public void testGetLazySet() {
48        AtomicReference ai = new AtomicReference(one);
49        assertSame(one, ai.get());
50        ai.lazySet(two);
51        assertSame(two, ai.get());
52        ai.lazySet(m3);
53        assertSame(m3, ai.get());
54    }
55
56    /**
57     * compareAndSet succeeds in changing value if equal to expected else fails
58     */
59    public void testCompareAndSet() {
60        AtomicReference ai = new AtomicReference(one);
61        assertTrue(ai.compareAndSet(one, two));
62        assertTrue(ai.compareAndSet(two, m4));
63        assertSame(m4, ai.get());
64        assertFalse(ai.compareAndSet(m5, seven));
65        assertSame(m4, ai.get());
66        assertTrue(ai.compareAndSet(m4, seven));
67        assertSame(seven, ai.get());
68    }
69
70    /**
71     * compareAndSet in one thread enables another waiting for value
72     * to succeed
73     */
74    public void testCompareAndSetInMultipleThreads() throws Exception {
75        final AtomicReference ai = new AtomicReference(one);
76        Thread t = new Thread(new CheckedRunnable() {
77            public void realRun() {
78                while (!ai.compareAndSet(two, three))
79                    Thread.yield();
80            }});
81
82        t.start();
83        assertTrue(ai.compareAndSet(one, two));
84        t.join(LONG_DELAY_MS);
85        assertFalse(t.isAlive());
86        assertSame(three, ai.get());
87    }
88
89    /**
90     * repeated weakCompareAndSet succeeds in changing value when equal
91     * to expected
92     */
93    public void testWeakCompareAndSet() {
94        AtomicReference ai = new AtomicReference(one);
95        while (!ai.weakCompareAndSet(one, two));
96        while (!ai.weakCompareAndSet(two, m4));
97        assertSame(m4, ai.get());
98        while (!ai.weakCompareAndSet(m4, seven));
99        assertSame(seven, ai.get());
100    }
101
102    /**
103     * getAndSet returns previous value and sets to given value
104     */
105    public void testGetAndSet() {
106        AtomicReference ai = new AtomicReference(one);
107        assertSame(one, ai.getAndSet(zero));
108        assertSame(zero, ai.getAndSet(m10));
109        assertSame(m10, ai.getAndSet(one));
110    }
111
112    /**
113     * a deserialized serialized atomic holds same value
114     */
115    public void testSerialization() throws Exception {
116        AtomicReference x = new AtomicReference();
117        AtomicReference y = serialClone(x);
118        assertNotSame(x, y);
119        x.set(one);
120        AtomicReference z = serialClone(x);
121        assertNotSame(y, z);
122        assertEquals(one, x.get());
123        assertEquals(null, y.get());
124        assertEquals(one, z.get());
125    }
126
127    /**
128     * toString returns current value.
129     */
130    public void testToString() {
131        AtomicReference<Integer> ai = new AtomicReference<Integer>(one);
132        assertEquals(one.toString(), ai.toString());
133        ai.set(two);
134        assertEquals(two.toString(), ai.toString());
135    }
136
137}
138