ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/test/tck/ReentrantReadWriteLockTest.java
(Generate patch)

Comparing jsr166/src/test/tck/ReentrantReadWriteLockTest.java (file contents):
Revision 1.1 by dl, Sun Aug 31 19:24:55 2003 UTC vs.
Revision 1.16 by dl, Wed Jan 7 01:02:17 2004 UTC

# Line 1 | Line 1
1   /*
2 < * Written by members of JCP JSR-166 Expert Group and released to the
3 < * public domain. Use, modify, and redistribute this code in any way
4 < * without acknowledgement. Other contributors include Andrew Wright,
5 < * Jeffrey Hayes, Pat Fischer, Mike Judd.
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   import junit.framework.*;
10   import java.util.concurrent.locks.*;
11   import java.util.concurrent.*;
12 + import java.io.*;
13 + import java.util.*;
14  
15 < public class ReentrantReadWriteLockTest extends TestCase {
13 <    static int HOLD_COUNT_TEST_LIMIT = 20;
14 <    
15 > public class ReentrantReadWriteLockTest extends JSR166TestCase {
16      public static void main(String[] args) {
17          junit.textui.TestRunner.run (suite());  
18      }
18    
19      public static Test suite() {
20          return new TestSuite(ReentrantReadWriteLockTest.class);
21      }
22  
23 +    /**
24 +     * A runnable calling lockInterruptibly
25 +     */
26 +    class InterruptibleLockRunnable implements Runnable {
27 +        final ReentrantReadWriteLock lock;
28 +        InterruptibleLockRunnable(ReentrantReadWriteLock l) { lock = l; }
29 +        public void run() {
30 +            try {
31 +                lock.writeLock().lockInterruptibly();
32 +            } catch(InterruptedException success){}
33 +        }
34 +    }
35 +
36 +
37 +    /**
38 +     * A runnable calling lockInterruptibly that expects to be
39 +     * interrupted
40 +     */
41 +    class InterruptedLockRunnable implements Runnable {
42 +        final ReentrantReadWriteLock lock;
43 +        InterruptedLockRunnable(ReentrantReadWriteLock l) { lock = l; }
44 +        public void run() {
45 +            try {
46 +                lock.writeLock().lockInterruptibly();
47 +                threadShouldThrow();
48 +            } catch(InterruptedException success){}
49 +        }
50 +    }
51 +
52 +    /**
53 +     * Subclass to expose protected methods
54 +     */
55 +    static class PublicReentrantReadWriteLock extends ReentrantReadWriteLock {
56 +        PublicReentrantReadWriteLock() { super(); }
57 +        public Collection<Thread> getQueuedThreads() {
58 +            return super.getQueuedThreads();
59 +        }
60 +        public Collection<Thread> getWaitingThreads(Condition c) {
61 +            return super.getWaitingThreads(c);
62 +        }
63 +    }
64 +
65 +    /**
66 +     * Constructor sets given fairness, and is in unlocked state
67 +     */
68 +    public void testConstructor() {
69 +        ReentrantReadWriteLock rl = new ReentrantReadWriteLock();
70 +        assertFalse(rl.isFair());
71 +        assertFalse(rl.isWriteLocked());
72 +        assertEquals(0, rl.getReadLockCount());
73 +        ReentrantReadWriteLock r2 = new ReentrantReadWriteLock(true);
74 +        assertTrue(r2.isFair());
75 +        assertFalse(r2.isWriteLocked());
76 +        assertEquals(0, r2.getReadLockCount());
77 +    }
78 +
79 +    /**
80 +     * write-locking and read-locking an unlocked lock succeed
81 +     */
82 +    public void testLock() {
83 +        ReentrantReadWriteLock rl = new ReentrantReadWriteLock();
84 +        rl.writeLock().lock();
85 +        assertTrue(rl.isWriteLocked());
86 +        assertTrue(rl.isWriteLockedByCurrentThread());
87 +        assertEquals(0, rl.getReadLockCount());
88 +        rl.writeLock().unlock();
89 +        assertFalse(rl.isWriteLocked());
90 +        assertFalse(rl.isWriteLockedByCurrentThread());
91 +        assertEquals(0, rl.getReadLockCount());
92 +        rl.readLock().lock();
93 +        assertFalse(rl.isWriteLocked());
94 +        assertFalse(rl.isWriteLockedByCurrentThread());
95 +        assertEquals(1, rl.getReadLockCount());
96 +        rl.readLock().unlock();
97 +        assertFalse(rl.isWriteLocked());
98 +        assertFalse(rl.isWriteLockedByCurrentThread());
99 +        assertEquals(0, rl.getReadLockCount());
100 +    }
101 +
102  
103 <    private static long SHORT_DELAY_MS = 100;
104 <    private static long MEDIUM_DELAY_MS = 1000;
26 <    private static long LONG_DELAY_MS = 10000;
27 <
28 <    /*
29 <     * Unlocks an unlocked lock, throws Illegal Monitor State
30 <     *
103 >    /**
104 >     * locking an unlocked fair lock succeeds
105       */
106 +    public void testFairLock() {
107 +        ReentrantReadWriteLock rl = new ReentrantReadWriteLock(true);
108 +        rl.writeLock().lock();
109 +        assertTrue(rl.isWriteLocked());
110 +        assertTrue(rl.isWriteLockedByCurrentThread());
111 +        assertEquals(0, rl.getReadLockCount());
112 +        rl.writeLock().unlock();
113 +        assertFalse(rl.isWriteLocked());
114 +        assertFalse(rl.isWriteLockedByCurrentThread());
115 +        assertEquals(0, rl.getReadLockCount());
116 +        rl.readLock().lock();
117 +        assertFalse(rl.isWriteLocked());
118 +        assertFalse(rl.isWriteLockedByCurrentThread());
119 +        assertEquals(1, rl.getReadLockCount());
120 +        rl.readLock().unlock();
121 +        assertFalse(rl.isWriteLocked());
122 +        assertFalse(rl.isWriteLockedByCurrentThread());
123 +        assertEquals(0, rl.getReadLockCount());
124 +    }
125 +
126 +    /**
127 +     * getWriteHoldCount returns number of recursive holds
128 +     */
129 +    public void testGetHoldCount() {
130 +        ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
131 +        for(int i = 1; i <= SIZE; i++) {
132 +            lock.writeLock().lock();
133 +            assertEquals(i,lock.getWriteHoldCount());
134 +        }
135 +        for(int i = SIZE; i > 0; i--) {
136 +            lock.writeLock().unlock();
137 +            assertEquals(i-1,lock.getWriteHoldCount());
138 +        }
139 +    }
140      
141 <    public void testIllegalMonitorStateException(){
141 >
142 >    /**
143 >     * write-unlocking an unlocked lock throws IllegalMonitorStateException
144 >     */
145 >    public void testUnlock_IllegalMonitorStateException() {
146          ReentrantReadWriteLock rl = new ReentrantReadWriteLock();
147 <        try{
147 >        try {
148              rl.writeLock().unlock();
149 <            fail("Should of thown Illegal Monitor State Exception");
149 >            shouldThrow();
150 >        } catch(IllegalMonitorStateException success){}
151 >    }
152  
39        }catch(IllegalMonitorStateException sucess){}
153  
154 +    /**
155 +     * write-lockInterruptibly is interruptible
156 +     */
157 +    public void testWriteLockInterruptibly_Interrupted() {
158 +        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
159 +        Thread t = new Thread(new Runnable() {
160 +                public void run() {
161 +                    try {
162 +                        lock.writeLock().lockInterruptibly();
163 +                        lock.writeLock().unlock();
164 +                        lock.writeLock().lockInterruptibly();
165 +                        lock.writeLock().unlock();
166 +                    } catch(InterruptedException success){}
167 +                }
168 +            });
169 +        try {
170 +            lock.writeLock().lock();
171 +            t.start();
172 +            t.interrupt();
173 +            lock.writeLock().unlock();
174 +            t.join();
175 +        } catch(Exception e){
176 +            unexpectedException();
177 +        }
178 +    }
179  
180 +    /**
181 +     * timed write-tryLock is interruptible
182 +     */
183 +    public void testWriteTryLock_Interrupted() {
184 +        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
185 +        lock.writeLock().lock();
186 +        Thread t = new Thread(new Runnable() {
187 +                public void run() {
188 +                    try {
189 +                        lock.writeLock().tryLock(1000,TimeUnit.MILLISECONDS);
190 +                        threadShouldThrow();
191 +                    } catch(InterruptedException success){}
192 +                }
193 +            });
194 +        try {
195 +            t.start();
196 +            t.interrupt();
197 +            lock.writeLock().unlock();
198 +            t.join();
199 +        } catch(Exception e){
200 +            unexpectedException();
201 +        }
202 +    }
203 +
204 +    /**
205 +     * read-lockInterruptibly is interruptible
206 +     */
207 +    public void testReadLockInterruptibly_Interrupted() {
208 +        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
209 +        lock.writeLock().lock();
210 +        Thread t = new Thread(new Runnable() {
211 +                public void run() {
212 +                    try {
213 +                        lock.readLock().lockInterruptibly();
214 +                    } catch(InterruptedException success){}
215 +                }
216 +            });
217 +        try {
218 +            t.start();
219 +            t.interrupt();
220 +            lock.writeLock().unlock();
221 +            t.join();
222 +        } catch(Exception e){
223 +            unexpectedException();
224 +        }
225 +    }
226 +
227 +    /**
228 +     * timed read-tryLock is interruptible
229 +     */
230 +    public void testReadTryLock_Interrupted() {
231 +        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
232 +        lock.writeLock().lock();
233 +        Thread t = new Thread(new Runnable() {
234 +                public void run() {
235 +                    try {
236 +                        lock.readLock().tryLock(1000,TimeUnit.MILLISECONDS);
237 +                        threadShouldThrow();
238 +                    } catch(InterruptedException success){}
239 +                }
240 +            });
241 +        try {
242 +            t.start();
243 +            t.interrupt();
244 +            t.join();
245 +        } catch(Exception e){
246 +            unexpectedException();
247 +        }
248      }
249 +
250      
251 <    /*
252 <     * makes a lock, locks it, tries to aquire the lock in another thread
46 <     * interrupts that thread and waits for an interrupted Exception to
47 <     * be thrown.
251 >    /**
252 >     * write-tryLock fails if locked
253       */
254 +    public void testWriteTryLockWhenLocked() {
255 +        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
256 +        lock.writeLock().lock();
257 +        Thread t = new Thread(new Runnable() {
258 +                public void run() {
259 +                    threadAssertFalse(lock.writeLock().tryLock());
260 +                }
261 +            });
262 +        try {
263 +            t.start();
264 +            t.join();
265 +            lock.writeLock().unlock();
266 +        } catch(Exception e){
267 +            unexpectedException();
268 +        }
269 +    }
270  
271 <    public void testInterruptedException(){
271 >    /**
272 >     * read-tryLock fails if locked
273 >     */
274 >    public void testReadTryLockWhenLocked() {
275          final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
276          lock.writeLock().lock();
277          Thread t = new Thread(new Runnable() {
278 <                public void run(){
279 <                    try{
280 <                        lock.writeLock().lockInterruptibly();
281 <                        fail("should throw");
282 <                    }catch(InterruptedException sucess){}
278 >                public void run() {
279 >                    threadAssertFalse(lock.readLock().tryLock());
280 >                }
281 >            });
282 >        try {
283 >            t.start();
284 >            t.join();
285 >            lock.writeLock().unlock();
286 >        } catch(Exception e){
287 >            unexpectedException();
288 >        }
289 >    }
290 >
291 >    /**
292 >     * Multiple threads can hold a read lock when not write-locked
293 >     */
294 >    public void testMultipleReadLocks() {
295 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
296 >        lock.readLock().lock();
297 >        Thread t = new Thread(new Runnable() {
298 >                public void run() {
299 >                    threadAssertTrue(lock.readLock().tryLock());
300 >                    lock.readLock().unlock();
301 >                }
302 >            });
303 >        try {
304 >            t.start();
305 >            t.join();
306 >            lock.readLock().unlock();
307 >        } catch(Exception e){
308 >            unexpectedException();
309 >        }
310 >    }
311 >
312 >    /**
313 >     * A writelock succeeds after reading threads unlock
314 >     */
315 >    public void testWriteAfterMultipleReadLocks() {
316 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
317 >        lock.readLock().lock();
318 >        Thread t1 = new Thread(new Runnable() {
319 >                public void run() {
320 >                    lock.readLock().lock();
321 >                    lock.readLock().unlock();
322 >                }
323 >            });
324 >        Thread t2 = new Thread(new Runnable() {
325 >                public void run() {
326 >                    lock.writeLock().lock();
327 >                    lock.writeLock().unlock();
328 >                }
329 >            });
330 >
331 >        try {
332 >            t1.start();
333 >            t2.start();
334 >            Thread.sleep(SHORT_DELAY_MS);
335 >            lock.readLock().unlock();
336 >            t1.join(MEDIUM_DELAY_MS);
337 >            t2.join(MEDIUM_DELAY_MS);
338 >            assertTrue(!t1.isAlive());
339 >            assertTrue(!t2.isAlive());
340 >          
341 >        } catch(Exception e){
342 >            unexpectedException();
343 >        }
344 >    }
345 >
346 >    /**
347 >     * Readlocks succeed after a writing thread unlocks
348 >     */
349 >    public void testReadAfterWriteLock() {
350 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
351 >        lock.writeLock().lock();
352 >        Thread t1 = new Thread(new Runnable() {
353 >                public void run() {
354 >                    lock.readLock().lock();
355 >                    lock.readLock().unlock();
356 >                }
357 >            });
358 >        Thread t2 = new Thread(new Runnable() {
359 >                public void run() {
360 >                    lock.readLock().lock();
361 >                    lock.readLock().unlock();
362 >                }
363 >            });
364 >
365 >        try {
366 >            t1.start();
367 >            t2.start();
368 >            Thread.sleep(SHORT_DELAY_MS);
369 >            lock.writeLock().unlock();
370 >            t1.join(MEDIUM_DELAY_MS);
371 >            t2.join(MEDIUM_DELAY_MS);
372 >            assertTrue(!t1.isAlive());
373 >            assertTrue(!t2.isAlive());
374 >          
375 >        } catch(Exception e){
376 >            unexpectedException();
377 >        }
378 >    }
379 >
380 >
381 >    /**
382 >     * Read tryLock succeeds if readlocked but not writelocked
383 >     */
384 >    public void testTryLockWhenReadLocked() {
385 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
386 >        lock.readLock().lock();
387 >        Thread t = new Thread(new Runnable() {
388 >                public void run() {
389 >                    threadAssertTrue(lock.readLock().tryLock());
390 >                    lock.readLock().unlock();
391                  }
392              });
393 <        t.start();
394 <        t.interrupt();
395 <        lock.writeLock().unlock();
393 >        try {
394 >            t.start();
395 >            t.join();
396 >            lock.readLock().unlock();
397 >        } catch(Exception e){
398 >            unexpectedException();
399 >        }
400      }
401  
402 <    /*
403 <     * tests for interrupted exception on a timed wait
404 <     *
402 >    
403 >
404 >    /**
405 >     * write tryLock fails when readlocked
406       */
407 +    public void testWriteTryLockWhenReadLocked() {
408 +        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
409 +        lock.readLock().lock();
410 +        Thread t = new Thread(new Runnable() {
411 +                public void run() {
412 +                    threadAssertFalse(lock.writeLock().tryLock());
413 +                }
414 +            });
415 +        try {
416 +            t.start();
417 +            t.join();
418 +            lock.readLock().unlock();
419 +        } catch(Exception e){
420 +            unexpectedException();
421 +        }
422 +    }
423 +
424      
425  
426 <    public void testInterruptedException2(){
426 >    /**
427 >     * write timed tryLock times out if locked
428 >     */
429 >    public void testWriteTryLock_Timeout() {
430          final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
431          lock.writeLock().lock();
432          Thread t = new Thread(new Runnable() {
433 <                public void run(){
434 <                    try{
435 <                        lock.writeLock().tryLock(1000,TimeUnit.MILLISECONDS);
436 <                        fail("should throw");
437 <                    }catch(InterruptedException sucess){}
433 >                public void run() {
434 >                    try {
435 >                        threadAssertFalse(lock.writeLock().tryLock(1, TimeUnit.MILLISECONDS));
436 >                    } catch (Exception ex) {
437 >                        threadUnexpectedException();
438 >                    }
439                  }
440              });
441 <        t.start();
442 <        t.interrupt();
441 >        try {
442 >            t.start();
443 >            t.join();
444 >            lock.writeLock().unlock();
445 >        } catch(Exception e){
446 >            unexpectedException();
447 >        }
448 >    }
449 >
450 >    /**
451 >     * read timed tryLock times out if write-locked
452 >     */
453 >    public void testReadTryLock_Timeout() {
454 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
455 >        lock.writeLock().lock();
456 >        Thread t = new Thread(new Runnable() {
457 >                public void run() {
458 >                    try {
459 >                        threadAssertFalse(lock.readLock().tryLock(1, TimeUnit.MILLISECONDS));
460 >                    } catch (Exception ex) {
461 >                        threadUnexpectedException();
462 >                    }
463 >                }
464 >            });
465 >        try {
466 >            t.start();
467 >            t.join();
468 >            lock.writeLock().unlock();
469 >        } catch(Exception e){
470 >            unexpectedException();
471 >        }
472 >    }
473 >
474 >
475 >    /**
476 >     * write lockInterruptibly succeeds if lock free else is interruptible
477 >     */
478 >    public void testWriteLockInterruptibly() {
479 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
480 >        try {
481 >            lock.writeLock().lockInterruptibly();
482 >        } catch(Exception e) {
483 >            unexpectedException();
484 >        }
485 >        Thread t = new Thread(new Runnable() {
486 >                public void run() {
487 >                    try {
488 >                        lock.writeLock().lockInterruptibly();
489 >                        threadShouldThrow();
490 >                    }
491 >                    catch(InterruptedException success) {
492 >                    }
493 >                }
494 >            });
495 >        try {
496 >            t.start();
497 >            t.interrupt();
498 >            t.join();
499 >            lock.writeLock().unlock();
500 >        } catch(Exception e){
501 >            unexpectedException();
502 >        }
503      }
504  
505 <    
505 >    /**
506 >     *  read lockInterruptibly succeeds if lock free else is interruptible
507 >     */
508 >    public void testReadLockInterruptibly() {
509 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
510 >        try {
511 >            lock.writeLock().lockInterruptibly();
512 >        } catch(Exception e) {
513 >            unexpectedException();
514 >        }
515 >        Thread t = new Thread(new Runnable() {
516 >                public void run() {
517 >                    try {
518 >                        lock.readLock().lockInterruptibly();
519 >                        threadShouldThrow();
520 >                    }
521 >                    catch(InterruptedException success) {
522 >                    }
523 >                }
524 >            });
525 >        try {
526 >            t.start();
527 >            t.interrupt();
528 >            t.join();
529 >            lock.writeLock().unlock();
530 >        } catch(Exception e){
531 >            unexpectedException();
532 >        }
533 >    }
534  
535 <    /*
536 <     * current thread locks interruptibly the thread
91 <     * another thread tries to aquire the lock and blocks
92 <     * on the call. interrupt the attempted aquireLock
93 <     * assert that the first lock() call actually locked the lock
94 <     * assert that the current thread is the one holding the lock
535 >    /**
536 >     * Calling await without holding lock throws IllegalMonitorStateException
537       */
538 +    public void testAwait_IllegalMonitor() {
539 +        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
540 +        final Condition c = lock.writeLock().newCondition();
541 +        try {
542 +            c.await();
543 +            shouldThrow();
544 +        }
545 +        catch (IllegalMonitorStateException success) {
546 +        }
547 +        catch (Exception ex) {
548 +            shouldThrow();
549 +        }
550 +    }
551  
552 <    public void testLockedInterruptibly() {
552 >    /**
553 >     * Calling signal without holding lock throws IllegalMonitorStateException
554 >     */
555 >    public void testSignal_IllegalMonitor() {
556          final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
557 <        try {lock.writeLock().lockInterruptibly();} catch(Exception e) {}
557 >        final Condition c = lock.writeLock().newCondition();
558 >        try {
559 >            c.signal();
560 >            shouldThrow();
561 >        }
562 >        catch (IllegalMonitorStateException success) {
563 >        }
564 >        catch (Exception ex) {
565 >            unexpectedException();
566 >        }
567 >    }
568 >
569 >    /**
570 >     * awaitNanos without a signal times out
571 >     */
572 >    public void testAwaitNanos_Timeout() {
573 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
574 >        final Condition c = lock.writeLock().newCondition();
575 >        try {
576 >            lock.writeLock().lock();
577 >            long t = c.awaitNanos(100);
578 >            assertTrue(t <= 0);
579 >            lock.writeLock().unlock();
580 >        }
581 >        catch (Exception ex) {
582 >            unexpectedException();
583 >        }
584 >    }
585 >
586 >
587 >    /**
588 >     *  timed await without a signal times out
589 >     */
590 >    public void testAwait_Timeout() {
591 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
592 >        final Condition c = lock.writeLock().newCondition();
593 >        try {
594 >            lock.writeLock().lock();
595 >            assertFalse(c.await(10, TimeUnit.MILLISECONDS));
596 >            lock.writeLock().unlock();
597 >        }
598 >        catch (Exception ex) {
599 >            unexpectedException();
600 >        }
601 >    }
602 >
603 >    /**
604 >     * awaitUntil without a signal times out
605 >     */
606 >    public void testAwaitUntil_Timeout() {
607 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
608 >        final Condition c = lock.writeLock().newCondition();
609 >        try {
610 >            lock.writeLock().lock();
611 >            java.util.Date d = new java.util.Date();
612 >            assertFalse(c.awaitUntil(new java.util.Date(d.getTime() + 10)));
613 >            lock.writeLock().unlock();
614 >        }
615 >        catch (Exception ex) {
616 >            unexpectedException();
617 >        }
618 >    }
619 >
620 >    /**
621 >     * await returns when signalled
622 >     */
623 >    public void testAwait() {
624 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
625 >        final Condition c = lock.writeLock().newCondition();
626          Thread t = new Thread(new Runnable() {
627                  public void run() {
628                      try {
629 <                        lock.writeLock().lockInterruptibly();
630 <                        fail("Failed to generate an Interrupted Exception");
629 >                        lock.writeLock().lock();
630 >                        c.await();
631 >                        lock.writeLock().unlock();
632                      }
633 <                    catch(InterruptedException e) {}
633 >                    catch(InterruptedException e) {
634 >                        threadUnexpectedException();
635 >                    }
636                  }
637              });
638 <        t.start();
639 <        t.interrupt();
638 >
639 >        try {
640 >            t.start();
641 >            Thread.sleep(SHORT_DELAY_MS);
642 >            lock.writeLock().lock();
643 >            c.signal();
644 >            lock.writeLock().unlock();
645 >            t.join(SHORT_DELAY_MS);
646 >            assertFalse(t.isAlive());
647 >        }
648 >        catch (Exception ex) {
649 >            unexpectedException();
650 >        }
651 >    }
652 >
653 >    /**
654 >     * awaitUninterruptibly doesn't abort on interrupt
655 >     */
656 >    public void testAwaitUninterruptibly() {
657 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
658 >        final Condition c = lock.writeLock().newCondition();
659 >        Thread t = new Thread(new Runnable() {
660 >                public void run() {
661 >                    lock.writeLock().lock();
662 >                    c.awaitUninterruptibly();
663 >                    lock.writeLock().unlock();
664 >                }
665 >            });
666 >
667 >        try {
668 >            t.start();
669 >            Thread.sleep(SHORT_DELAY_MS);
670 >            t.interrupt();
671 >            lock.writeLock().lock();
672 >            c.signal();
673 >            lock.writeLock().unlock();
674 >            assert(t.isInterrupted());
675 >            t.join(SHORT_DELAY_MS);
676 >            assertFalse(t.isAlive());
677 >        }
678 >        catch (Exception ex) {
679 >            unexpectedException();
680 >        }
681 >    }
682 >
683 >    /**
684 >     * await is interruptible
685 >     */
686 >    public void testAwait_Interrupt() {
687 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
688 >        final Condition c = lock.writeLock().newCondition();
689 >        Thread t = new Thread(new Runnable() {
690 >                public void run() {
691 >                    try {
692 >                        lock.writeLock().lock();
693 >                        c.await();
694 >                        lock.writeLock().unlock();
695 >                        threadShouldThrow();
696 >                    }
697 >                    catch(InterruptedException success) {
698 >                    }
699 >                }
700 >            });
701 >
702 >        try {
703 >            t.start();
704 >            Thread.sleep(SHORT_DELAY_MS);
705 >            t.interrupt();
706 >            t.join(SHORT_DELAY_MS);
707 >            assertFalse(t.isAlive());
708 >        }
709 >        catch (Exception ex) {
710 >            unexpectedException();
711 >        }
712 >    }
713 >
714 >    /**
715 >     * awaitNanos is interruptible
716 >     */
717 >    public void testAwaitNanos_Interrupt() {
718 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
719 >        final Condition c = lock.writeLock().newCondition();
720 >        Thread t = new Thread(new Runnable() {
721 >                public void run() {
722 >                    try {
723 >                        lock.writeLock().lock();
724 >                        c.awaitNanos(SHORT_DELAY_MS * 2 * 1000000);
725 >                        lock.writeLock().unlock();
726 >                        threadShouldThrow();
727 >                    }
728 >                    catch(InterruptedException success) {
729 >                    }
730 >                }
731 >            });
732 >
733 >        try {
734 >            t.start();
735 >            Thread.sleep(SHORT_DELAY_MS);
736 >            t.interrupt();
737 >            t.join(SHORT_DELAY_MS);
738 >            assertFalse(t.isAlive());
739 >        }
740 >        catch (Exception ex) {
741 >            unexpectedException();
742 >        }
743 >    }
744 >
745 >    /**
746 >     * awaitUntil is interruptible
747 >     */
748 >    public void testAwaitUntil_Interrupt() {
749 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
750 >        final Condition c = lock.writeLock().newCondition();
751 >        Thread t = new Thread(new Runnable() {
752 >                public void run() {
753 >                    try {
754 >                        lock.writeLock().lock();
755 >                        java.util.Date d = new java.util.Date();
756 >                        c.awaitUntil(new java.util.Date(d.getTime() + 10000));
757 >                        lock.writeLock().unlock();
758 >                        threadShouldThrow();
759 >                    }
760 >                    catch(InterruptedException success) {
761 >                    }
762 >                }
763 >            });
764 >
765 >        try {
766 >            t.start();
767 >            Thread.sleep(SHORT_DELAY_MS);
768 >            t.interrupt();
769 >            t.join(SHORT_DELAY_MS);
770 >            assertFalse(t.isAlive());
771 >        }
772 >        catch (Exception ex) {
773 >            unexpectedException();
774 >        }
775 >    }
776 >
777 >    /**
778 >     * signalAll wakes up all threads
779 >     */
780 >    public void testSignalAll() {
781 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();      
782 >        final Condition c = lock.writeLock().newCondition();
783 >        Thread t1 = new Thread(new Runnable() {
784 >                public void run() {
785 >                    try {
786 >                        lock.writeLock().lock();
787 >                        c.await();
788 >                        lock.writeLock().unlock();
789 >                    }
790 >                    catch(InterruptedException e) {
791 >                        threadUnexpectedException();
792 >                    }
793 >                }
794 >            });
795 >
796 >        Thread t2 = new Thread(new Runnable() {
797 >                public void run() {
798 >                    try {
799 >                        lock.writeLock().lock();
800 >                        c.await();
801 >                        lock.writeLock().unlock();
802 >                    }
803 >                    catch(InterruptedException e) {
804 >                        threadUnexpectedException();
805 >                    }
806 >                }
807 >            });
808 >
809 >        try {
810 >            t1.start();
811 >            t2.start();
812 >            Thread.sleep(SHORT_DELAY_MS);
813 >            lock.writeLock().lock();
814 >            c.signalAll();
815 >            lock.writeLock().unlock();
816 >            t1.join(SHORT_DELAY_MS);
817 >            t2.join(SHORT_DELAY_MS);
818 >            assertFalse(t1.isAlive());
819 >            assertFalse(t2.isAlive());
820 >        }
821 >        catch (Exception ex) {
822 >            unexpectedException();
823 >        }
824 >    }
825 >
826 >    /**
827 >     * A serialized lock deserializes as unlocked
828 >     */
829 >    public void testSerialization() {
830 >        ReentrantReadWriteLock l = new ReentrantReadWriteLock();
831 >        l.readLock().lock();
832 >        l.readLock().unlock();
833 >
834 >        try {
835 >            ByteArrayOutputStream bout = new ByteArrayOutputStream(10000);
836 >            ObjectOutputStream out = new ObjectOutputStream(new BufferedOutputStream(bout));
837 >            out.writeObject(l);
838 >            out.close();
839 >
840 >            ByteArrayInputStream bin = new ByteArrayInputStream(bout.toByteArray());
841 >            ObjectInputStream in = new ObjectInputStream(new BufferedInputStream(bin));
842 >            ReentrantReadWriteLock r = (ReentrantReadWriteLock) in.readObject();
843 >            r.readLock().lock();
844 >            r.readLock().unlock();
845 >        } catch(Exception e){
846 >            e.printStackTrace();
847 >            unexpectedException();
848 >        }
849 >    }
850 >
851 >    /**
852 >     * hasQueuedThreads reports whether there are waiting threads
853 >     */
854 >    public void testhasQueuedThreads() {
855 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
856 >        Thread t1 = new Thread(new InterruptedLockRunnable(lock));
857 >        Thread t2 = new Thread(new InterruptibleLockRunnable(lock));
858 >        try {
859 >            assertFalse(lock.hasQueuedThreads());
860 >            lock.writeLock().lock();
861 >            t1.start();
862 >            Thread.sleep(SHORT_DELAY_MS);
863 >            assertTrue(lock.hasQueuedThreads());
864 >            t2.start();
865 >            Thread.sleep(SHORT_DELAY_MS);
866 >            assertTrue(lock.hasQueuedThreads());
867 >            t1.interrupt();
868 >            Thread.sleep(SHORT_DELAY_MS);
869 >            assertTrue(lock.hasQueuedThreads());
870 >            lock.writeLock().unlock();
871 >            Thread.sleep(SHORT_DELAY_MS);
872 >            assertFalse(lock.hasQueuedThreads());
873 >            t1.join();
874 >            t2.join();
875 >        } catch(Exception e){
876 >            unexpectedException();
877 >        }
878 >    }
879 >
880 >    /**
881 >     * getQueueLength reports number of waiting threads
882 >     */
883 >    public void testGetQueueLength() {
884 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
885 >        Thread t1 = new Thread(new InterruptedLockRunnable(lock));
886 >        Thread t2 = new Thread(new InterruptibleLockRunnable(lock));
887 >        try {
888 >            assertEquals(0, lock.getQueueLength());
889 >            lock.writeLock().lock();
890 >            t1.start();
891 >            Thread.sleep(SHORT_DELAY_MS);
892 >            assertEquals(1, lock.getQueueLength());
893 >            t2.start();
894 >            Thread.sleep(SHORT_DELAY_MS);
895 >            assertEquals(2, lock.getQueueLength());
896 >            t1.interrupt();
897 >            Thread.sleep(SHORT_DELAY_MS);
898 >            assertEquals(1, lock.getQueueLength());
899 >            lock.writeLock().unlock();
900 >            Thread.sleep(SHORT_DELAY_MS);
901 >            assertEquals(0, lock.getQueueLength());
902 >            t1.join();
903 >            t2.join();
904 >        } catch(Exception e){
905 >            unexpectedException();
906 >        }
907 >    }
908 >
909 >    /**
910 >     * getQueuedThreads includes waiting threads
911 >     */
912 >    public void testGetQueuedThreads() {
913 >        final PublicReentrantReadWriteLock lock = new PublicReentrantReadWriteLock();
914 >        Thread t1 = new Thread(new InterruptedLockRunnable(lock));
915 >        Thread t2 = new Thread(new InterruptibleLockRunnable(lock));
916 >        try {
917 >            assertTrue(lock.getQueuedThreads().isEmpty());
918 >            lock.writeLock().lock();
919 >            assertTrue(lock.getQueuedThreads().isEmpty());
920 >            t1.start();
921 >            Thread.sleep(SHORT_DELAY_MS);
922 >            assertTrue(lock.getQueuedThreads().contains(t1));
923 >            t2.start();
924 >            Thread.sleep(SHORT_DELAY_MS);
925 >            assertTrue(lock.getQueuedThreads().contains(t1));
926 >            assertTrue(lock.getQueuedThreads().contains(t2));
927 >            t1.interrupt();
928 >            Thread.sleep(SHORT_DELAY_MS);
929 >            assertFalse(lock.getQueuedThreads().contains(t1));
930 >            assertTrue(lock.getQueuedThreads().contains(t2));
931 >            lock.writeLock().unlock();
932 >            Thread.sleep(SHORT_DELAY_MS);
933 >            assertTrue(lock.getQueuedThreads().isEmpty());
934 >            t1.join();
935 >            t2.join();
936 >        } catch(Exception e){
937 >            unexpectedException();
938 >        }
939 >    }
940 >
941 >    /**
942 >     * hasWaiters throws NPE if null
943 >     */
944 >    public void testHasWaitersNPE() {
945 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
946 >        try {
947 >            lock.hasWaiters(null);
948 >            shouldThrow();
949 >        } catch (NullPointerException success) {
950 >        } catch (Exception ex) {
951 >            unexpectedException();
952 >        }
953 >    }
954 >
955 >    /**
956 >     * getWaitQueueLength throws NPE if null
957 >     */
958 >    public void testGetWaitQueueLengthNPE() {
959 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
960 >        try {
961 >            lock.getWaitQueueLength(null);
962 >            shouldThrow();
963 >        } catch (NullPointerException success) {
964 >        } catch (Exception ex) {
965 >            unexpectedException();
966 >        }
967 >    }
968 >
969 >
970 >    /**
971 >     * getWaitingThreads throws NPE if null
972 >     */
973 >    public void testGetWaitingThreadsNPE() {
974 >        final PublicReentrantReadWriteLock lock = new PublicReentrantReadWriteLock();
975 >        try {
976 >            lock.getWaitingThreads(null);
977 >            shouldThrow();
978 >        } catch (NullPointerException success) {
979 >        } catch (Exception ex) {
980 >            unexpectedException();
981 >        }
982 >    }
983 >
984 >    /**
985 >     * hasWaiters throws IAE if not owned
986 >     */
987 >    public void testHasWaitersIAE() {
988 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
989 >        final Condition c = (lock.writeLock().newCondition());
990 >        final ReentrantReadWriteLock lock2 = new ReentrantReadWriteLock();
991 >        try {
992 >            lock2.hasWaiters(c);
993 >            shouldThrow();
994 >        } catch (IllegalArgumentException success) {
995 >        } catch (Exception ex) {
996 >            unexpectedException();
997 >        }
998 >    }
999 >
1000 >    /**
1001 >     * hasWaiters throws IMSE if not locked
1002 >     */
1003 >    public void testHasWaitersIMSE() {
1004 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
1005 >        final Condition c = (lock.writeLock().newCondition());
1006 >        try {
1007 >            lock.hasWaiters(c);
1008 >            shouldThrow();
1009 >        } catch (IllegalMonitorStateException success) {
1010 >        } catch (Exception ex) {
1011 >            unexpectedException();
1012 >        }
1013 >    }
1014 >
1015 >
1016 >    /**
1017 >     * getWaitQueueLength throws IAE if not owned
1018 >     */
1019 >    public void testGetWaitQueueLengthIAE() {
1020 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
1021 >        final Condition c = (lock.writeLock().newCondition());
1022 >        final ReentrantReadWriteLock lock2 = new ReentrantReadWriteLock();
1023 >        try {
1024 >            lock2.getWaitQueueLength(c);
1025 >            shouldThrow();
1026 >        } catch (IllegalArgumentException success) {
1027 >        } catch (Exception ex) {
1028 >            unexpectedException();
1029 >        }
1030 >    }
1031 >
1032 >    /**
1033 >     * getWaitQueueLength throws IMSE if not locked
1034 >     */
1035 >    public void testGetWaitQueueLengthIMSE() {
1036 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
1037 >        final Condition c = (lock.writeLock().newCondition());
1038 >        try {
1039 >            lock.getWaitQueueLength(c);
1040 >            shouldThrow();
1041 >        } catch (IllegalMonitorStateException success) {
1042 >        } catch (Exception ex) {
1043 >            unexpectedException();
1044 >        }
1045 >    }
1046 >
1047 >
1048 >    /**
1049 >     * getWaitingThreads throws IAE if not owned
1050 >     */
1051 >    public void testGetWaitingThreadsIAE() {
1052 >        final PublicReentrantReadWriteLock lock = new PublicReentrantReadWriteLock();  
1053 >        final Condition c = (lock.writeLock().newCondition());
1054 >        final PublicReentrantReadWriteLock lock2 = new PublicReentrantReadWriteLock();  
1055 >        try {
1056 >            lock2.getWaitingThreads(c);
1057 >            shouldThrow();
1058 >        } catch (IllegalArgumentException success) {
1059 >        } catch (Exception ex) {
1060 >            unexpectedException();
1061 >        }
1062 >    }
1063 >
1064 >    /**
1065 >     * getWaitingThreads throws IMSE if not locked
1066 >     */
1067 >    public void testGetWaitingThreadsIMSE() {
1068 >        final PublicReentrantReadWriteLock lock = new PublicReentrantReadWriteLock();  
1069 >        final Condition c = (lock.writeLock().newCondition());
1070 >        try {
1071 >            lock.getWaitingThreads(c);
1072 >            shouldThrow();
1073 >        } catch (IllegalMonitorStateException success) {
1074 >        } catch (Exception ex) {
1075 >            unexpectedException();
1076 >        }
1077 >    }
1078 >
1079 >
1080 >    /**
1081 >     * hasWaiters returns true when a thread is waiting, else false
1082 >     */
1083 >    public void testHasWaiters() {
1084 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
1085 >        final Condition c = (lock.writeLock().newCondition());
1086 >        Thread t = new Thread(new Runnable() {
1087 >                public void run() {
1088 >                    try {
1089 >                        lock.writeLock().lock();
1090 >                        threadAssertFalse(lock.hasWaiters(c));
1091 >                        threadAssertEquals(0, lock.getWaitQueueLength(c));
1092 >                        c.await();
1093 >                        lock.writeLock().unlock();
1094 >                    }
1095 >                    catch(InterruptedException e) {
1096 >                        threadUnexpectedException();
1097 >                    }
1098 >                }
1099 >            });
1100 >
1101 >        try {
1102 >            t.start();
1103 >            Thread.sleep(SHORT_DELAY_MS);
1104 >            lock.writeLock().lock();
1105 >            assertTrue(lock.hasWaiters(c));
1106 >            assertEquals(1, lock.getWaitQueueLength(c));
1107 >            c.signal();
1108 >            lock.writeLock().unlock();
1109 >            Thread.sleep(SHORT_DELAY_MS);
1110 >            lock.writeLock().lock();
1111 >            assertFalse(lock.hasWaiters(c));
1112 >            assertEquals(0, lock.getWaitQueueLength(c));
1113 >            lock.writeLock().unlock();
1114 >            t.join(SHORT_DELAY_MS);
1115 >            assertFalse(t.isAlive());
1116 >        }
1117 >        catch (Exception ex) {
1118 >            unexpectedException();
1119 >        }
1120 >    }
1121 >
1122 >    /**
1123 >     * getWaitQueueLength returns number of waiting threads
1124 >     */
1125 >    public void testGetWaitQueueLength() {
1126 >        final ReentrantReadWriteLock lock = new ReentrantReadWriteLock();
1127 >        final Condition c = (lock.writeLock().newCondition());
1128 >        Thread t = new Thread(new Runnable() {
1129 >                public void run() {
1130 >                    try {
1131 >                        lock.writeLock().lock();
1132 >                        threadAssertFalse(lock.hasWaiters(c));
1133 >                        threadAssertEquals(0, lock.getWaitQueueLength(c));
1134 >                        c.await();
1135 >                        lock.writeLock().unlock();
1136 >                    }
1137 >                    catch(InterruptedException e) {
1138 >                        threadUnexpectedException();
1139 >                    }
1140 >                }
1141 >            });
1142 >
1143 >        try {
1144 >            t.start();
1145 >            Thread.sleep(SHORT_DELAY_MS);
1146 >            lock.writeLock().lock();
1147 >            assertTrue(lock.hasWaiters(c));
1148 >            assertEquals(1, lock.getWaitQueueLength(c));
1149 >            c.signal();
1150 >            lock.writeLock().unlock();
1151 >            Thread.sleep(SHORT_DELAY_MS);
1152 >            lock.writeLock().lock();
1153 >            assertFalse(lock.hasWaiters(c));
1154 >            assertEquals(0, lock.getWaitQueueLength(c));
1155 >            lock.writeLock().unlock();
1156 >            t.join(SHORT_DELAY_MS);
1157 >            assertFalse(t.isAlive());
1158 >        }
1159 >        catch (Exception ex) {
1160 >            unexpectedException();
1161 >        }
1162 >    }
1163 >
1164 >
1165 >    /**
1166 >     * getWaitingThreads returns only and all waiting threads
1167 >     */
1168 >    public void testGetWaitingThreads() {
1169 >        final PublicReentrantReadWriteLock lock = new PublicReentrantReadWriteLock();  
1170 >        final Condition c = lock.writeLock().newCondition();
1171 >        Thread t1 = new Thread(new Runnable() {
1172 >                public void run() {
1173 >                    try {
1174 >                        lock.writeLock().lock();
1175 >                        threadAssertTrue(lock.getWaitingThreads(c).isEmpty());
1176 >                        c.await();
1177 >                        lock.writeLock().unlock();
1178 >                    }
1179 >                    catch(InterruptedException e) {
1180 >                        threadUnexpectedException();
1181 >                    }
1182 >                }
1183 >            });
1184 >
1185 >        Thread t2 = new Thread(new Runnable() {
1186 >                public void run() {
1187 >                    try {
1188 >                        lock.writeLock().lock();
1189 >                        threadAssertFalse(lock.getWaitingThreads(c).isEmpty());
1190 >                        c.await();
1191 >                        lock.writeLock().unlock();
1192 >                    }
1193 >                    catch(InterruptedException e) {
1194 >                        threadUnexpectedException();
1195 >                    }
1196 >                }
1197 >            });
1198 >
1199 >        try {
1200 >            lock.writeLock().lock();
1201 >            assertTrue(lock.getWaitingThreads(c).isEmpty());
1202 >            lock.writeLock().unlock();
1203 >            t1.start();
1204 >            Thread.sleep(SHORT_DELAY_MS);
1205 >            t2.start();
1206 >            Thread.sleep(SHORT_DELAY_MS);
1207 >            lock.writeLock().lock();
1208 >            assertTrue(lock.hasWaiters(c));
1209 >            assertTrue(lock.getWaitingThreads(c).contains(t1));
1210 >            assertTrue(lock.getWaitingThreads(c).contains(t2));
1211 >            c.signalAll();
1212 >            lock.writeLock().unlock();
1213 >            Thread.sleep(SHORT_DELAY_MS);
1214 >            lock.writeLock().lock();
1215 >            assertFalse(lock.hasWaiters(c));
1216 >            assertTrue(lock.getWaitingThreads(c).isEmpty());
1217 >            lock.writeLock().unlock();
1218 >            t1.join(SHORT_DELAY_MS);
1219 >            t2.join(SHORT_DELAY_MS);
1220 >            assertFalse(t1.isAlive());
1221 >            assertFalse(t2.isAlive());
1222 >        }
1223 >        catch (Exception ex) {
1224 >            unexpectedException();
1225 >        }
1226      }
112    
1227  
1228   }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines