ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/test/tck/AbstractQueuedSynchronizerTest.java
Revision: 1.5
Committed: Tue Dec 30 15:48:38 2003 UTC (20 years, 4 months ago) by dl
Branch: MAIN
Changes since 1.4: +5 -13 lines
Log Message:
Avoid cache thrashing

File Contents

# User Rev Content
1 dl 1.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/licenses/publicdomain
5     * Other contributors include Andrew Wright, Jeffrey Hayes,
6     * Pat Fisher, Mike Judd.
7     */
8    
9    
10     import junit.framework.*;
11     import java.util.*;
12     import java.util.concurrent.*;
13     import java.util.concurrent.locks.*;
14     import java.io.*;
15    
16     public class AbstractQueuedSynchronizerTest extends JSR166TestCase {
17     public static void main(String[] args) {
18     junit.textui.TestRunner.run (suite());
19     }
20     public static Test suite() {
21     return new TestSuite(AbstractQueuedSynchronizerTest.class);
22     }
23    
24     /**
25     * A simple mutex class, from the AbstractQueuedSynchronizer
26     * javadoc. All tests exercise this as a sample user extension.
27     * Other methods/features of AbstractQueuedSynchronizerTest are
28     * tested implicitly in ReentrantLock, ReentrantReadWriteLock, and
29     * Semaphore test classes
30     */
31     static class Mutex implements Lock, java.io.Serializable {
32     private static class Sync extends AbstractQueuedSynchronizer {
33 dl 1.3 public int acquireExclusiveState(boolean isQueued, int acquires) {
34 dl 1.1 assert acquires == 1; // Does not use multiple acquires
35 dl 1.5 return compareAndSet(0, 1)? 0 : -1;
36 dl 1.1 }
37    
38     public boolean releaseExclusiveState(int releases) {
39 dl 1.5 set(0);
40 dl 1.1 return true;
41     }
42    
43     public void checkConditionAccess(Thread thread, boolean waiting) {
44 dl 1.5 if (get() == 0) throw new IllegalMonitorStateException();
45 dl 1.1 }
46    
47     Condition newCondition() { return new ConditionObject(); }
48    
49     private void readObject(ObjectInputStream s) throws IOException, ClassNotFoundException {
50     s.defaultReadObject();
51 dl 1.5 set(0); // reset to unlocked state
52 dl 1.1 }
53     }
54    
55     private final Sync sync = new Sync();
56     public boolean tryLock() {
57 dl 1.3 return sync.acquireExclusiveState(false, 1) >= 0;
58 dl 1.2 }
59     public void lock() {
60 dl 1.3 sync.acquireExclusiveUninterruptibly(1);
61 dl 1.1 }
62     public void lockInterruptibly() throws InterruptedException {
63     sync.acquireExclusiveInterruptibly(1);
64     }
65     public boolean tryLock(long timeout, TimeUnit unit) throws InterruptedException {
66     return sync.acquireExclusiveTimed(1, unit.toNanos(timeout));
67     }
68     public void unlock() { sync.releaseExclusive(1); }
69     public Condition newCondition() { return sync.newCondition(); }
70 dl 1.5 public boolean isLocked() { return sync.get() != 0; }
71 dl 1.1 public boolean hasQueuedThreads() { return sync.hasQueuedThreads(); }
72     }
73    
74     /**
75     * A runnable calling lockInterruptibly
76     */
77     class InterruptibleLockRunnable implements Runnable {
78     final Mutex lock;
79     InterruptibleLockRunnable(Mutex l) { lock = l; }
80     public void run() {
81     try {
82     lock.lockInterruptibly();
83     } catch(InterruptedException success){}
84     }
85     }
86    
87    
88     /**
89     * A runnable calling lockInterruptibly that expects to be
90     * interrupted
91     */
92     class InterruptedLockRunnable implements Runnable {
93     final Mutex lock;
94     InterruptedLockRunnable(Mutex l) { lock = l; }
95     public void run() {
96     try {
97     lock.lockInterruptibly();
98     threadShouldThrow();
99     } catch(InterruptedException success){}
100     }
101     }
102    
103     /**
104     * locking an unlocked lock succeeds
105     */
106     public void testLock() {
107     Mutex rl = new Mutex();
108     rl.lock();
109     assertTrue(rl.isLocked());
110     rl.unlock();
111     }
112    
113     /**
114 dl 1.4 * tryLock on an unlocked lock succeeds
115 dl 1.1 */
116     public void testTryLock() {
117     Mutex rl = new Mutex();
118     assertTrue(rl.tryLock());
119     assertTrue(rl.isLocked());
120     rl.unlock();
121     }
122    
123     /**
124     * hasQueuedThreads reports whether there are waiting threads
125     */
126     public void testhasQueuedThreads() {
127     final Mutex lock = new Mutex();
128     Thread t1 = new Thread(new InterruptedLockRunnable(lock));
129     Thread t2 = new Thread(new InterruptibleLockRunnable(lock));
130     try {
131     assertFalse(lock.hasQueuedThreads());
132     lock.lock();
133     t1.start();
134     Thread.sleep(SHORT_DELAY_MS);
135     assertTrue(lock.hasQueuedThreads());
136     t2.start();
137     Thread.sleep(SHORT_DELAY_MS);
138     assertTrue(lock.hasQueuedThreads());
139     t1.interrupt();
140     Thread.sleep(SHORT_DELAY_MS);
141     assertTrue(lock.hasQueuedThreads());
142     lock.unlock();
143     Thread.sleep(SHORT_DELAY_MS);
144     assertFalse(lock.hasQueuedThreads());
145     t1.join();
146     t2.join();
147     } catch(Exception e){
148     unexpectedException();
149     }
150     }
151    
152     /**
153 dl 1.4 * timed tryLock is interruptible.
154 dl 1.1 */
155     public void testInterruptedException2() {
156     final Mutex lock = new Mutex();
157     lock.lock();
158     Thread t = new Thread(new Runnable() {
159     public void run() {
160     try {
161     lock.tryLock(MEDIUM_DELAY_MS,TimeUnit.MILLISECONDS);
162     threadShouldThrow();
163     } catch(InterruptedException success){}
164     }
165     });
166     try {
167     t.start();
168     t.interrupt();
169     } catch(Exception e){
170     unexpectedException();
171     }
172     }
173    
174    
175     /**
176 dl 1.4 * TryLock on a locked lock fails
177 dl 1.1 */
178     public void testTryLockWhenLocked() {
179     final Mutex lock = new Mutex();
180     lock.lock();
181     Thread t = new Thread(new Runnable() {
182     public void run() {
183     threadAssertFalse(lock.tryLock());
184     }
185     });
186     try {
187     t.start();
188     t.join();
189     lock.unlock();
190     } catch(Exception e){
191     unexpectedException();
192     }
193     }
194    
195     /**
196 dl 1.4 * Timed tryLock on a locked lock times out
197 dl 1.1 */
198     public void testTryLock_Timeout() {
199     final Mutex lock = new Mutex();
200     lock.lock();
201     Thread t = new Thread(new Runnable() {
202     public void run() {
203     try {
204     threadAssertFalse(lock.tryLock(1, TimeUnit.MILLISECONDS));
205     } catch (Exception ex) {
206     threadUnexpectedException();
207     }
208     }
209     });
210     try {
211     t.start();
212     t.join();
213     lock.unlock();
214     } catch(Exception e){
215     unexpectedException();
216     }
217     }
218    
219    
220     /**
221     * isLocked is true when locked and false when not
222     */
223     public void testIsLocked() {
224     final Mutex lock = new Mutex();
225     lock.lock();
226     assertTrue(lock.isLocked());
227     lock.unlock();
228     assertFalse(lock.isLocked());
229     Thread t = new Thread(new Runnable() {
230     public void run() {
231     lock.lock();
232     try {
233     Thread.sleep(SMALL_DELAY_MS);
234     }
235     catch(Exception e) {
236     threadUnexpectedException();
237     }
238     lock.unlock();
239     }
240     });
241     try {
242     t.start();
243     Thread.sleep(SHORT_DELAY_MS);
244     assertTrue(lock.isLocked());
245     t.join();
246     assertFalse(lock.isLocked());
247     } catch(Exception e){
248     unexpectedException();
249     }
250     }
251    
252    
253     /**
254     * lockInterruptibly is interruptible.
255     */
256     public void testLockInterruptibly1() {
257     final Mutex lock = new Mutex();
258     lock.lock();
259     Thread t = new Thread(new InterruptedLockRunnable(lock));
260     try {
261     t.start();
262     t.interrupt();
263     lock.unlock();
264     t.join();
265     } catch(Exception e){
266     unexpectedException();
267     }
268     }
269    
270     /**
271     * lockInterruptibly succeeds when unlocked, else is interruptible
272     */
273     public void testLockInterruptibly2() {
274     final Mutex lock = new Mutex();
275     try {
276     lock.lockInterruptibly();
277     } catch(Exception e) {
278     unexpectedException();
279     }
280     Thread t = new Thread(new InterruptedLockRunnable(lock));
281     try {
282     t.start();
283     t.interrupt();
284     assertTrue(lock.isLocked());
285     t.join();
286     } catch(Exception e){
287     unexpectedException();
288     }
289     }
290    
291     /**
292     * Calling await without holding lock throws IllegalMonitorStateException
293     */
294     public void testAwait_IllegalMonitor() {
295     final Mutex lock = new Mutex();
296     final Condition c = lock.newCondition();
297     try {
298     c.await();
299     shouldThrow();
300     }
301     catch (IllegalMonitorStateException success) {
302     }
303     catch (Exception ex) {
304     unexpectedException();
305     }
306     }
307    
308     /**
309     * Calling signal without holding lock throws IllegalMonitorStateException
310     */
311     public void testSignal_IllegalMonitor() {
312     final Mutex lock = new Mutex();
313     final Condition c = lock.newCondition();
314     try {
315     c.signal();
316     shouldThrow();
317     }
318     catch (IllegalMonitorStateException success) {
319     }
320     catch (Exception ex) {
321     unexpectedException();
322     }
323     }
324    
325     /**
326     * awaitNanos without a signal times out
327     */
328     public void testAwaitNanos_Timeout() {
329     final Mutex lock = new Mutex();
330     final Condition c = lock.newCondition();
331     try {
332     lock.lock();
333     long t = c.awaitNanos(100);
334     assertTrue(t <= 0);
335     lock.unlock();
336     }
337     catch (Exception ex) {
338     unexpectedException();
339     }
340     }
341    
342     /**
343     * timed await without a signal times out
344     */
345     public void testAwait_Timeout() {
346     final Mutex lock = new Mutex();
347     final Condition c = lock.newCondition();
348     try {
349     lock.lock();
350     assertFalse(c.await(SHORT_DELAY_MS, TimeUnit.MILLISECONDS));
351     lock.unlock();
352     }
353     catch (Exception ex) {
354     unexpectedException();
355     }
356     }
357    
358     /**
359     * awaitUntil without a signal times out
360     */
361     public void testAwaitUntil_Timeout() {
362     final Mutex lock = new Mutex();
363     final Condition c = lock.newCondition();
364     try {
365     lock.lock();
366     java.util.Date d = new java.util.Date();
367     assertFalse(c.awaitUntil(new java.util.Date(d.getTime() + 10)));
368     lock.unlock();
369     }
370     catch (Exception ex) {
371     unexpectedException();
372     }
373     }
374    
375     /**
376     * await returns when signalled
377     */
378     public void testAwait() {
379     final Mutex lock = new Mutex();
380     final Condition c = lock.newCondition();
381     Thread t = new Thread(new Runnable() {
382     public void run() {
383     try {
384     lock.lock();
385     c.await();
386     lock.unlock();
387     }
388     catch(InterruptedException e) {
389     threadUnexpectedException();
390     }
391     }
392     });
393    
394     try {
395     t.start();
396     Thread.sleep(SHORT_DELAY_MS);
397     lock.lock();
398     c.signal();
399     lock.unlock();
400     t.join(SHORT_DELAY_MS);
401     assertFalse(t.isAlive());
402     }
403     catch (Exception ex) {
404     unexpectedException();
405     }
406     }
407    
408     }