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

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

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines