ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/test/tck/AbstractQueuedSynchronizerTest.java
Revision: 1.27
Committed: Wed Nov 18 08:26:24 2009 UTC (14 years, 5 months ago) by jsr166
Branch: MAIN
Changes since 1.26: +2 -1 lines
Log Message:
missing call to join

File Contents

# Content
1 /*
2 * Written by Doug Lea with assistance from members of JCP JSR-166
3 * Expert Group and released to the public domain, as explained at
4 * http://creativecommons.org/licenses/publicdomain
5 * Other contributors include Andrew Wright, Jeffrey Hayes,
6 * Pat Fisher, Mike Judd.
7 */
8
9
10 import junit.framework.*;
11 import java.util.*;
12 import java.util.concurrent.*;
13 import java.util.concurrent.locks.*;
14 import java.io.*;
15
16 public class AbstractQueuedSynchronizerTest extends JSR166TestCase {
17 public static void main(String[] args) {
18 junit.textui.TestRunner.run (suite());
19 }
20 public static Test suite() {
21 return new TestSuite(AbstractQueuedSynchronizerTest.class);
22 }
23
24 /**
25 * A simple mutex class, adapted from the
26 * AbstractQueuedSynchronizer javadoc. Exclusive acquire tests
27 * exercise this as a sample user extension. Other
28 * methods/features of AbstractQueuedSynchronizerTest are tested
29 * via other test classes, including those for ReentrantLock,
30 * ReentrantReadWriteLock, and Semaphore
31 */
32 static class Mutex extends AbstractQueuedSynchronizer {
33 public boolean isHeldExclusively() { return getState() == 1; }
34
35 public boolean tryAcquire(int acquires) {
36 assertTrue(acquires == 1);
37 return compareAndSetState(0, 1);
38 }
39
40 public boolean tryRelease(int releases) {
41 if (getState() == 0) throw new IllegalMonitorStateException();
42 setState(0);
43 return true;
44 }
45
46 public AbstractQueuedSynchronizer.ConditionObject newCondition() { return new AbstractQueuedSynchronizer.ConditionObject(); }
47
48 }
49
50
51 /**
52 * A simple latch class, to test shared mode.
53 */
54 static class BooleanLatch extends AbstractQueuedSynchronizer {
55 public boolean isSignalled() { return getState() != 0; }
56
57 public int tryAcquireShared(int ignore) {
58 return isSignalled()? 1 : -1;
59 }
60
61 public boolean tryReleaseShared(int ignore) {
62 setState(1);
63 return true;
64 }
65 }
66
67 /**
68 * A runnable calling acquireInterruptibly
69 */
70 class InterruptibleSyncRunnable implements Runnable {
71 final Mutex sync;
72 InterruptibleSyncRunnable(Mutex l) { sync = l; }
73 public void run() {
74 try {
75 sync.acquireInterruptibly(1);
76 } catch (InterruptedException success) {}
77 }
78 }
79
80
81 /**
82 * A runnable calling acquireInterruptibly that expects to be
83 * interrupted
84 */
85 class InterruptedSyncRunnable implements Runnable {
86 final Mutex sync;
87 InterruptedSyncRunnable(Mutex l) { sync = l; }
88 public void run() {
89 try {
90 sync.acquireInterruptibly(1);
91 threadShouldThrow();
92 } catch (InterruptedException success) {}
93 }
94 }
95
96 /**
97 * isHeldExclusively is false upon construction
98 */
99 public void testIsHeldExclusively() {
100 Mutex rl = new Mutex();
101 assertFalse(rl.isHeldExclusively());
102 }
103
104 /**
105 * acquiring released sync succeeds
106 */
107 public void testAcquire() {
108 Mutex rl = new Mutex();
109 rl.acquire(1);
110 assertTrue(rl.isHeldExclusively());
111 rl.release(1);
112 assertFalse(rl.isHeldExclusively());
113 }
114
115 /**
116 * tryAcquire on an released sync succeeds
117 */
118 public void testTryAcquire() {
119 Mutex rl = new Mutex();
120 assertTrue(rl.tryAcquire(1));
121 assertTrue(rl.isHeldExclusively());
122 rl.release(1);
123 }
124
125 /**
126 * hasQueuedThreads reports whether there are waiting threads
127 */
128 public void testhasQueuedThreads() throws InterruptedException {
129 final Mutex sync = new Mutex();
130 Thread t1 = new Thread(new InterruptedSyncRunnable(sync));
131 Thread t2 = new Thread(new InterruptibleSyncRunnable(sync));
132 assertFalse(sync.hasQueuedThreads());
133 sync.acquire(1);
134 t1.start();
135 Thread.sleep(SHORT_DELAY_MS);
136 assertTrue(sync.hasQueuedThreads());
137 t2.start();
138 Thread.sleep(SHORT_DELAY_MS);
139 assertTrue(sync.hasQueuedThreads());
140 t1.interrupt();
141 Thread.sleep(SHORT_DELAY_MS);
142 assertTrue(sync.hasQueuedThreads());
143 sync.release(1);
144 Thread.sleep(SHORT_DELAY_MS);
145 assertFalse(sync.hasQueuedThreads());
146 t1.join();
147 t2.join();
148 }
149
150 /**
151 * isQueued(null) throws NPE
152 */
153 public void testIsQueuedNPE() {
154 final Mutex sync = new Mutex();
155 try {
156 sync.isQueued(null);
157 shouldThrow();
158 } catch (NullPointerException success) {}
159 }
160
161 /**
162 * isQueued reports whether a thread is queued.
163 */
164 public void testIsQueued() throws InterruptedException {
165 final Mutex sync = new Mutex();
166 Thread t1 = new Thread(new InterruptedSyncRunnable(sync));
167 Thread t2 = new Thread(new InterruptibleSyncRunnable(sync));
168 assertFalse(sync.isQueued(t1));
169 assertFalse(sync.isQueued(t2));
170 sync.acquire(1);
171 t1.start();
172 Thread.sleep(SHORT_DELAY_MS);
173 assertTrue(sync.isQueued(t1));
174 t2.start();
175 Thread.sleep(SHORT_DELAY_MS);
176 assertTrue(sync.isQueued(t1));
177 assertTrue(sync.isQueued(t2));
178 t1.interrupt();
179 Thread.sleep(SHORT_DELAY_MS);
180 assertFalse(sync.isQueued(t1));
181 assertTrue(sync.isQueued(t2));
182 sync.release(1);
183 Thread.sleep(SHORT_DELAY_MS);
184 assertFalse(sync.isQueued(t1));
185 Thread.sleep(SHORT_DELAY_MS);
186 assertFalse(sync.isQueued(t2));
187 t1.join();
188 t2.join();
189 }
190
191 /**
192 * getFirstQueuedThread returns first waiting thread or null if none
193 */
194 public void testGetFirstQueuedThread() throws InterruptedException {
195 final Mutex sync = new Mutex();
196 Thread t1 = new Thread(new InterruptedSyncRunnable(sync));
197 Thread t2 = new Thread(new InterruptibleSyncRunnable(sync));
198 assertNull(sync.getFirstQueuedThread());
199 sync.acquire(1);
200 t1.start();
201 Thread.sleep(SHORT_DELAY_MS);
202 assertEquals(t1, sync.getFirstQueuedThread());
203 t2.start();
204 Thread.sleep(SHORT_DELAY_MS);
205 assertEquals(t1, sync.getFirstQueuedThread());
206 t1.interrupt();
207 Thread.sleep(SHORT_DELAY_MS);
208 Thread.sleep(SHORT_DELAY_MS);
209 assertEquals(t2, sync.getFirstQueuedThread());
210 sync.release(1);
211 Thread.sleep(SHORT_DELAY_MS);
212 assertNull(sync.getFirstQueuedThread());
213 t1.join();
214 t2.join();
215 }
216
217
218 /**
219 * hasContended reports false if no thread has ever blocked, else true
220 */
221 public void testHasContended() throws InterruptedException {
222 final Mutex sync = new Mutex();
223 Thread t1 = new Thread(new InterruptedSyncRunnable(sync));
224 Thread t2 = new Thread(new InterruptibleSyncRunnable(sync));
225 assertFalse(sync.hasContended());
226 sync.acquire(1);
227 t1.start();
228 Thread.sleep(SHORT_DELAY_MS);
229 assertTrue(sync.hasContended());
230 t2.start();
231 Thread.sleep(SHORT_DELAY_MS);
232 assertTrue(sync.hasContended());
233 t1.interrupt();
234 Thread.sleep(SHORT_DELAY_MS);
235 assertTrue(sync.hasContended());
236 sync.release(1);
237 Thread.sleep(SHORT_DELAY_MS);
238 assertTrue(sync.hasContended());
239 t1.join();
240 t2.join();
241 }
242
243 /**
244 * getQueuedThreads includes waiting threads
245 */
246 public void testGetQueuedThreads() throws InterruptedException {
247 final Mutex sync = new Mutex();
248 Thread t1 = new Thread(new InterruptedSyncRunnable(sync));
249 Thread t2 = new Thread(new InterruptibleSyncRunnable(sync));
250 assertTrue(sync.getQueuedThreads().isEmpty());
251 sync.acquire(1);
252 assertTrue(sync.getQueuedThreads().isEmpty());
253 t1.start();
254 Thread.sleep(SHORT_DELAY_MS);
255 assertTrue(sync.getQueuedThreads().contains(t1));
256 t2.start();
257 Thread.sleep(SHORT_DELAY_MS);
258 assertTrue(sync.getQueuedThreads().contains(t1));
259 assertTrue(sync.getQueuedThreads().contains(t2));
260 t1.interrupt();
261 Thread.sleep(SHORT_DELAY_MS);
262 assertFalse(sync.getQueuedThreads().contains(t1));
263 assertTrue(sync.getQueuedThreads().contains(t2));
264 sync.release(1);
265 Thread.sleep(SHORT_DELAY_MS);
266 assertTrue(sync.getQueuedThreads().isEmpty());
267 t1.join();
268 t2.join();
269 }
270
271 /**
272 * getExclusiveQueuedThreads includes waiting threads
273 */
274 public void testGetExclusiveQueuedThreads() throws InterruptedException {
275 final Mutex sync = new Mutex();
276 Thread t1 = new Thread(new InterruptedSyncRunnable(sync));
277 Thread t2 = new Thread(new InterruptibleSyncRunnable(sync));
278 assertTrue(sync.getExclusiveQueuedThreads().isEmpty());
279 sync.acquire(1);
280 assertTrue(sync.getExclusiveQueuedThreads().isEmpty());
281 t1.start();
282 Thread.sleep(SHORT_DELAY_MS);
283 assertTrue(sync.getExclusiveQueuedThreads().contains(t1));
284 t2.start();
285 Thread.sleep(SHORT_DELAY_MS);
286 assertTrue(sync.getExclusiveQueuedThreads().contains(t1));
287 assertTrue(sync.getExclusiveQueuedThreads().contains(t2));
288 t1.interrupt();
289 Thread.sleep(SHORT_DELAY_MS);
290 assertFalse(sync.getExclusiveQueuedThreads().contains(t1));
291 assertTrue(sync.getExclusiveQueuedThreads().contains(t2));
292 sync.release(1);
293 Thread.sleep(SHORT_DELAY_MS);
294 assertTrue(sync.getExclusiveQueuedThreads().isEmpty());
295 t1.join();
296 t2.join();
297 }
298
299 /**
300 * getSharedQueuedThreads does not include exclusively waiting threads
301 */
302 public void testGetSharedQueuedThreads() throws InterruptedException {
303 final Mutex sync = new Mutex();
304 Thread t1 = new Thread(new InterruptedSyncRunnable(sync));
305 Thread t2 = new Thread(new InterruptibleSyncRunnable(sync));
306 assertTrue(sync.getSharedQueuedThreads().isEmpty());
307 sync.acquire(1);
308 assertTrue(sync.getSharedQueuedThreads().isEmpty());
309 t1.start();
310 Thread.sleep(SHORT_DELAY_MS);
311 assertTrue(sync.getSharedQueuedThreads().isEmpty());
312 t2.start();
313 Thread.sleep(SHORT_DELAY_MS);
314 assertTrue(sync.getSharedQueuedThreads().isEmpty());
315 t1.interrupt();
316 Thread.sleep(SHORT_DELAY_MS);
317 assertTrue(sync.getSharedQueuedThreads().isEmpty());
318 sync.release(1);
319 Thread.sleep(SHORT_DELAY_MS);
320 assertTrue(sync.getSharedQueuedThreads().isEmpty());
321 t1.join();
322 t2.join();
323 }
324
325 /**
326 * tryAcquireNanos is interruptible.
327 */
328 public void testInterruptedException2() throws InterruptedException {
329 final Mutex sync = new Mutex();
330 sync.acquire(1);
331 Thread t = new Thread(new Runnable() {
332 public void run() {
333 try {
334 sync.tryAcquireNanos(1, MEDIUM_DELAY_MS * 1000 * 1000);
335 threadShouldThrow();
336 } catch (InterruptedException success) {}
337 }
338 });
339
340 t.start();
341 t.interrupt();
342 t.join();
343 }
344
345
346 /**
347 * TryAcquire on exclusively held sync fails
348 */
349 public void testTryAcquireWhenSynced() throws InterruptedException {
350 final Mutex sync = new Mutex();
351 sync.acquire(1);
352 Thread t = new Thread(new Runnable() {
353 public void run() {
354 threadAssertFalse(sync.tryAcquire(1));
355 }
356 });
357
358 t.start();
359 t.join();
360 sync.release(1);
361 }
362
363 /**
364 * tryAcquireNanos on an exclusively held sync times out
365 */
366 public void testAcquireNanos_Timeout() throws InterruptedException {
367 final Mutex sync = new Mutex();
368 sync.acquire(1);
369 Thread t = new Thread(new Runnable() {
370 public void run() {
371 try {
372 threadAssertFalse(sync.tryAcquireNanos(1, 1000 * 1000));
373 } catch (Exception ex) {
374 threadUnexpectedException();
375 }
376 }
377 });
378
379 t.start();
380 t.join();
381 sync.release(1);
382 }
383
384
385 /**
386 * getState is true when acquired and false when not
387 */
388 public void testGetState() throws InterruptedException {
389 final Mutex sync = new Mutex();
390 sync.acquire(1);
391 assertTrue(sync.isHeldExclusively());
392 sync.release(1);
393 assertFalse(sync.isHeldExclusively());
394 Thread t = new Thread(new Runnable() {
395 public void run() {
396 sync.acquire(1);
397 try {
398 Thread.sleep(SMALL_DELAY_MS);
399 }
400 catch (Exception e) {
401 threadUnexpectedException();
402 }
403 sync.release(1);
404 }
405 });
406
407 t.start();
408 Thread.sleep(SHORT_DELAY_MS);
409 assertTrue(sync.isHeldExclusively());
410 t.join();
411 assertFalse(sync.isHeldExclusively());
412 }
413
414
415 /**
416 * acquireInterruptibly is interruptible.
417 */
418 public void testAcquireInterruptibly1() throws InterruptedException {
419 final Mutex sync = new Mutex();
420 sync.acquire(1);
421 Thread t = new Thread(new InterruptedSyncRunnable(sync));
422
423 t.start();
424 Thread.sleep(SHORT_DELAY_MS);
425 t.interrupt();
426 Thread.sleep(SHORT_DELAY_MS);
427 sync.release(1);
428 t.join();
429 }
430
431 /**
432 * acquireInterruptibly succeeds when released, else is interruptible
433 */
434 public void testAcquireInterruptibly2() throws InterruptedException {
435 final Mutex sync = new Mutex();
436 sync.acquireInterruptibly(1);
437 Thread t = new Thread(new InterruptedSyncRunnable(sync));
438 t.start();
439 t.interrupt();
440 assertTrue(sync.isHeldExclusively());
441 t.join();
442 }
443
444 /**
445 * owns is true for a condition created by sync else false
446 */
447 public void testOwns() {
448 final Mutex sync = new Mutex();
449 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
450 final Mutex sync2 = new Mutex();
451 assertTrue(sync.owns(c));
452 assertFalse(sync2.owns(c));
453 }
454
455 /**
456 * Calling await without holding sync throws IllegalMonitorStateException
457 */
458 public void testAwait_IllegalMonitor() throws InterruptedException {
459 final Mutex sync = new Mutex();
460 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
461 try {
462 c.await();
463 shouldThrow();
464 }
465 catch (IllegalMonitorStateException success) {}
466 }
467
468 /**
469 * Calling signal without holding sync throws IllegalMonitorStateException
470 */
471 public void testSignal_IllegalMonitor() {
472 final Mutex sync = new Mutex();
473 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
474 try {
475 c.signal();
476 shouldThrow();
477 }
478 catch (IllegalMonitorStateException success) {}
479 }
480
481 /**
482 * awaitNanos without a signal times out
483 */
484 public void testAwaitNanos_Timeout() throws InterruptedException {
485 final Mutex sync = new Mutex();
486 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
487 sync.acquire(1);
488 long t = c.awaitNanos(100);
489 assertTrue(t <= 0);
490 sync.release(1);
491 }
492
493 /**
494 * Timed await without a signal times out
495 */
496 public void testAwait_Timeout() throws InterruptedException {
497 final Mutex sync = new Mutex();
498 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
499 sync.acquire(1);
500 assertFalse(c.await(SHORT_DELAY_MS, TimeUnit.MILLISECONDS));
501 sync.release(1);
502 }
503
504 /**
505 * awaitUntil without a signal times out
506 */
507 public void testAwaitUntil_Timeout() throws InterruptedException {
508 final Mutex sync = new Mutex();
509 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
510 sync.acquire(1);
511 java.util.Date d = new java.util.Date();
512 assertFalse(c.awaitUntil(new java.util.Date(d.getTime() + 10)));
513 sync.release(1);
514 }
515
516 /**
517 * await returns when signalled
518 */
519 public void testAwait() throws InterruptedException {
520 final Mutex sync = new Mutex();
521 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
522 Thread t = new Thread(new Runnable() {
523 public void run() {
524 try {
525 sync.acquire(1);
526 c.await();
527 sync.release(1);
528 }
529 catch (InterruptedException e) {
530 threadUnexpectedException();
531 }
532 }
533 });
534
535 t.start();
536 Thread.sleep(SHORT_DELAY_MS);
537 sync.acquire(1);
538 c.signal();
539 sync.release(1);
540 t.join(SHORT_DELAY_MS);
541 assertFalse(t.isAlive());
542 }
543
544
545
546 /**
547 * hasWaiters throws NPE if null
548 */
549 public void testHasWaitersNPE() {
550 final Mutex sync = new Mutex();
551 try {
552 sync.hasWaiters(null);
553 shouldThrow();
554 } catch (NullPointerException success) {}
555 }
556
557 /**
558 * getWaitQueueLength throws NPE if null
559 */
560 public void testGetWaitQueueLengthNPE() {
561 final Mutex sync = new Mutex();
562 try {
563 sync.getWaitQueueLength(null);
564 shouldThrow();
565 } catch (NullPointerException success) {}
566 }
567
568
569 /**
570 * getWaitingThreads throws NPE if null
571 */
572 public void testGetWaitingThreadsNPE() {
573 final Mutex sync = new Mutex();
574 try {
575 sync.getWaitingThreads(null);
576 shouldThrow();
577 } catch (NullPointerException success) {}
578 }
579
580
581 /**
582 * hasWaiters throws IAE if not owned
583 */
584 public void testHasWaitersIAE() {
585 final Mutex sync = new Mutex();
586 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
587 final Mutex sync2 = new Mutex();
588 try {
589 sync2.hasWaiters(c);
590 shouldThrow();
591 } catch (IllegalArgumentException success) {}
592 }
593
594 /**
595 * hasWaiters throws IMSE if not synced
596 */
597 public void testHasWaitersIMSE() {
598 final Mutex sync = new Mutex();
599 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
600 try {
601 sync.hasWaiters(c);
602 shouldThrow();
603 } catch (IllegalMonitorStateException success) {}
604 }
605
606
607 /**
608 * getWaitQueueLength throws IAE if not owned
609 */
610 public void testGetWaitQueueLengthIAE() {
611 final Mutex sync = new Mutex();
612 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
613 final Mutex sync2 = new Mutex();
614 try {
615 sync2.getWaitQueueLength(c);
616 shouldThrow();
617 } catch (IllegalArgumentException success) {}
618 }
619
620 /**
621 * getWaitQueueLength throws IMSE if not synced
622 */
623 public void testGetWaitQueueLengthIMSE() {
624 final Mutex sync = new Mutex();
625 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
626 try {
627 sync.getWaitQueueLength(c);
628 shouldThrow();
629 } catch (IllegalMonitorStateException success) {}
630 }
631
632
633 /**
634 * getWaitingThreads throws IAE if not owned
635 */
636 public void testGetWaitingThreadsIAE() {
637 final Mutex sync = new Mutex();
638 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
639 final Mutex sync2 = new Mutex();
640 try {
641 sync2.getWaitingThreads(c);
642 shouldThrow();
643 } catch (IllegalArgumentException success) {}
644 }
645
646 /**
647 * getWaitingThreads throws IMSE if not synced
648 */
649 public void testGetWaitingThreadsIMSE() {
650 final Mutex sync = new Mutex();
651 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
652 try {
653 sync.getWaitingThreads(c);
654 shouldThrow();
655 } catch (IllegalMonitorStateException success) {}
656 }
657
658
659
660 /**
661 * hasWaiters returns true when a thread is waiting, else false
662 */
663 public void testHasWaiters() throws InterruptedException {
664 final Mutex sync = new Mutex();
665 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
666 Thread t = new Thread(new Runnable() {
667 public void run() {
668 try {
669 sync.acquire(1);
670 threadAssertFalse(sync.hasWaiters(c));
671 threadAssertEquals(0, sync.getWaitQueueLength(c));
672 c.await();
673 sync.release(1);
674 }
675 catch (InterruptedException e) {
676 threadUnexpectedException();
677 }
678 }
679 });
680
681 t.start();
682 Thread.sleep(SHORT_DELAY_MS);
683 sync.acquire(1);
684 assertTrue(sync.hasWaiters(c));
685 assertEquals(1, sync.getWaitQueueLength(c));
686 c.signal();
687 sync.release(1);
688 Thread.sleep(SHORT_DELAY_MS);
689 sync.acquire(1);
690 assertFalse(sync.hasWaiters(c));
691 assertEquals(0, sync.getWaitQueueLength(c));
692 sync.release(1);
693 t.join(SHORT_DELAY_MS);
694 assertFalse(t.isAlive());
695 }
696
697 /**
698 * getWaitQueueLength returns number of waiting threads
699 */
700 public void testGetWaitQueueLength() throws InterruptedException {
701 final Mutex sync = new Mutex();
702 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
703 Thread t1 = new Thread(new Runnable() {
704 public void run() {
705 try {
706 sync.acquire(1);
707 threadAssertFalse(sync.hasWaiters(c));
708 threadAssertEquals(0, sync.getWaitQueueLength(c));
709 c.await();
710 sync.release(1);
711 }
712 catch (InterruptedException e) {
713 threadUnexpectedException();
714 }
715 }
716 });
717
718 Thread t2 = new Thread(new Runnable() {
719 public void run() {
720 try {
721 sync.acquire(1);
722 threadAssertTrue(sync.hasWaiters(c));
723 threadAssertEquals(1, sync.getWaitQueueLength(c));
724 c.await();
725 sync.release(1);
726 }
727 catch (InterruptedException e) {
728 threadUnexpectedException();
729 }
730 }
731 });
732
733 t1.start();
734 Thread.sleep(SHORT_DELAY_MS);
735 t2.start();
736 Thread.sleep(SHORT_DELAY_MS);
737 sync.acquire(1);
738 assertTrue(sync.hasWaiters(c));
739 assertEquals(2, sync.getWaitQueueLength(c));
740 c.signalAll();
741 sync.release(1);
742 Thread.sleep(SHORT_DELAY_MS);
743 sync.acquire(1);
744 assertFalse(sync.hasWaiters(c));
745 assertEquals(0, sync.getWaitQueueLength(c));
746 sync.release(1);
747 t1.join(SHORT_DELAY_MS);
748 t2.join(SHORT_DELAY_MS);
749 assertFalse(t1.isAlive());
750 assertFalse(t2.isAlive());
751 }
752
753 /**
754 * getWaitingThreads returns only and all waiting threads
755 */
756 public void testGetWaitingThreads() throws InterruptedException {
757 final Mutex sync = new Mutex();
758 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
759 Thread t1 = new Thread(new Runnable() {
760 public void run() {
761 try {
762 sync.acquire(1);
763 threadAssertTrue(sync.getWaitingThreads(c).isEmpty());
764 c.await();
765 sync.release(1);
766 }
767 catch (InterruptedException e) {
768 threadUnexpectedException();
769 }
770 }
771 });
772
773 Thread t2 = new Thread(new Runnable() {
774 public void run() {
775 try {
776 sync.acquire(1);
777 threadAssertFalse(sync.getWaitingThreads(c).isEmpty());
778 c.await();
779 sync.release(1);
780 }
781 catch (InterruptedException e) {
782 threadUnexpectedException();
783 }
784 }
785 });
786
787 sync.acquire(1);
788 assertTrue(sync.getWaitingThreads(c).isEmpty());
789 sync.release(1);
790 t1.start();
791 Thread.sleep(SHORT_DELAY_MS);
792 t2.start();
793 Thread.sleep(SHORT_DELAY_MS);
794 sync.acquire(1);
795 assertTrue(sync.hasWaiters(c));
796 assertTrue(sync.getWaitingThreads(c).contains(t1));
797 assertTrue(sync.getWaitingThreads(c).contains(t2));
798 c.signalAll();
799 sync.release(1);
800 Thread.sleep(SHORT_DELAY_MS);
801 sync.acquire(1);
802 assertFalse(sync.hasWaiters(c));
803 assertTrue(sync.getWaitingThreads(c).isEmpty());
804 sync.release(1);
805 t1.join(SHORT_DELAY_MS);
806 t2.join(SHORT_DELAY_MS);
807 assertFalse(t1.isAlive());
808 assertFalse(t2.isAlive());
809 }
810
811
812
813 /**
814 * awaitUninterruptibly doesn't abort on interrupt
815 */
816 public void testAwaitUninterruptibly() throws InterruptedException {
817 final Mutex sync = new Mutex();
818 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
819 Thread t = new Thread(new Runnable() {
820 public void run() {
821 sync.acquire(1);
822 c.awaitUninterruptibly();
823 sync.release(1);
824 }
825 });
826
827 t.start();
828 Thread.sleep(SHORT_DELAY_MS);
829 t.interrupt();
830 sync.acquire(1);
831 c.signal();
832 sync.release(1);
833 t.join(SHORT_DELAY_MS);
834 assertFalse(t.isAlive());
835 }
836
837 /**
838 * await is interruptible
839 */
840 public void testAwait_Interrupt() throws InterruptedException {
841 final Mutex sync = new Mutex();
842 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
843 Thread t = new Thread(new Runnable() {
844 public void run() {
845 try {
846 sync.acquire(1);
847 c.await();
848 sync.release(1);
849 threadShouldThrow();
850 }
851 catch (InterruptedException success) {
852 }
853 }
854 });
855
856 t.start();
857 Thread.sleep(SHORT_DELAY_MS);
858 t.interrupt();
859 t.join(SHORT_DELAY_MS);
860 assertFalse(t.isAlive());
861 }
862
863 /**
864 * awaitNanos is interruptible
865 */
866 public void testAwaitNanos_Interrupt() throws InterruptedException {
867 final Mutex sync = new Mutex();
868 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
869 Thread t = new Thread(new Runnable() {
870 public void run() {
871 try {
872 sync.acquire(1);
873 c.awaitNanos(1000 * 1000 * 1000); // 1 sec
874 sync.release(1);
875 threadShouldThrow();
876 }
877 catch (InterruptedException success) {
878 }
879 }
880 });
881
882 t.start();
883 Thread.sleep(SHORT_DELAY_MS);
884 t.interrupt();
885 t.join(SHORT_DELAY_MS);
886 assertFalse(t.isAlive());
887 }
888
889 /**
890 * awaitUntil is interruptible
891 */
892 public void testAwaitUntil_Interrupt() throws InterruptedException {
893 final Mutex sync = new Mutex();
894 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
895 Thread t = new Thread(new Runnable() {
896 public void run() {
897 try {
898 sync.acquire(1);
899 java.util.Date d = new java.util.Date();
900 c.awaitUntil(new java.util.Date(d.getTime() + 10000));
901 sync.release(1);
902 threadShouldThrow();
903 }
904 catch (InterruptedException success) {
905 }
906 }
907 });
908
909 t.start();
910 Thread.sleep(SHORT_DELAY_MS);
911 t.interrupt();
912 t.join(SHORT_DELAY_MS);
913 assertFalse(t.isAlive());
914 }
915
916 /**
917 * signalAll wakes up all threads
918 */
919 public void testSignalAll() throws InterruptedException {
920 final Mutex sync = new Mutex();
921 final AbstractQueuedSynchronizer.ConditionObject c = sync.newCondition();
922 Thread t1 = new Thread(new Runnable() {
923 public void run() {
924 try {
925 sync.acquire(1);
926 c.await();
927 sync.release(1);
928 }
929 catch (InterruptedException e) {
930 threadUnexpectedException();
931 }
932 }
933 });
934
935 Thread t2 = new Thread(new Runnable() {
936 public void run() {
937 try {
938 sync.acquire(1);
939 c.await();
940 sync.release(1);
941 }
942 catch (InterruptedException e) {
943 threadUnexpectedException();
944 }
945 }
946 });
947
948 t1.start();
949 t2.start();
950 Thread.sleep(SHORT_DELAY_MS);
951 sync.acquire(1);
952 c.signalAll();
953 sync.release(1);
954 t1.join(SHORT_DELAY_MS);
955 t2.join(SHORT_DELAY_MS);
956 assertFalse(t1.isAlive());
957 assertFalse(t2.isAlive());
958 }
959
960
961 /**
962 * toString indicates current state
963 */
964 public void testToString() {
965 Mutex sync = new Mutex();
966 String us = sync.toString();
967 assertTrue(us.indexOf("State = 0") >= 0);
968 sync.acquire(1);
969 String ls = sync.toString();
970 assertTrue(ls.indexOf("State = 1") >= 0);
971 }
972
973 /**
974 * A serialized AQS deserializes with current state
975 */
976 public void testSerialization() throws Exception {
977 Mutex l = new Mutex();
978 l.acquire(1);
979 assertTrue(l.isHeldExclusively());
980
981 ByteArrayOutputStream bout = new ByteArrayOutputStream(10000);
982 ObjectOutputStream out = new ObjectOutputStream(new BufferedOutputStream(bout));
983 out.writeObject(l);
984 out.close();
985
986 ByteArrayInputStream bin = new ByteArrayInputStream(bout.toByteArray());
987 ObjectInputStream in = new ObjectInputStream(new BufferedInputStream(bin));
988 Mutex r = (Mutex) in.readObject();
989 assertTrue(r.isHeldExclusively());
990 }
991
992
993 /**
994 * tryReleaseShared setting state changes getState
995 */
996 public void testGetStateWithReleaseShared() {
997 final BooleanLatch l = new BooleanLatch();
998 assertFalse(l.isSignalled());
999 l.releaseShared(0);
1000 assertTrue(l.isSignalled());
1001 }
1002
1003 /**
1004 * releaseShared has no effect when already signalled
1005 */
1006 public void testReleaseShared() {
1007 final BooleanLatch l = new BooleanLatch();
1008 assertFalse(l.isSignalled());
1009 l.releaseShared(0);
1010 assertTrue(l.isSignalled());
1011 l.releaseShared(0);
1012 assertTrue(l.isSignalled());
1013 }
1014
1015 /**
1016 * acquireSharedInterruptibly returns after release, but not before
1017 */
1018 public void testAcquireSharedInterruptibly() throws InterruptedException {
1019 final BooleanLatch l = new BooleanLatch();
1020
1021 Thread t = new Thread(new Runnable() {
1022 public void run() {
1023 try {
1024 threadAssertFalse(l.isSignalled());
1025 l.acquireSharedInterruptibly(0);
1026 threadAssertTrue(l.isSignalled());
1027 } catch (InterruptedException e) {
1028 threadUnexpectedException();
1029 }
1030 }
1031 });
1032
1033 t.start();
1034 assertFalse(l.isSignalled());
1035 Thread.sleep(SHORT_DELAY_MS);
1036 l.releaseShared(0);
1037 assertTrue(l.isSignalled());
1038 t.join();
1039 }
1040
1041
1042 /**
1043 * acquireSharedTimed returns after release
1044 */
1045 public void testAsquireSharedTimed() throws InterruptedException {
1046 final BooleanLatch l = new BooleanLatch();
1047
1048 Thread t = new Thread(new Runnable() {
1049 public void run() {
1050 try {
1051 threadAssertFalse(l.isSignalled());
1052 threadAssertTrue(l.tryAcquireSharedNanos(0, MEDIUM_DELAY_MS* 1000 * 1000));
1053 threadAssertTrue(l.isSignalled());
1054
1055 } catch (InterruptedException e) {
1056 threadUnexpectedException();
1057 }
1058 }
1059 });
1060
1061 t.start();
1062 assertFalse(l.isSignalled());
1063 Thread.sleep(SHORT_DELAY_MS);
1064 l.releaseShared(0);
1065 assertTrue(l.isSignalled());
1066 t.join();
1067 }
1068
1069 /**
1070 * acquireSharedInterruptibly throws IE if interrupted before released
1071 */
1072 public void testAcquireSharedInterruptibly_InterruptedException() throws InterruptedException {
1073 final BooleanLatch l = new BooleanLatch();
1074 Thread t = new Thread(new Runnable() {
1075 public void run() {
1076 try {
1077 threadAssertFalse(l.isSignalled());
1078 l.acquireSharedInterruptibly(0);
1079 threadShouldThrow();
1080 } catch (InterruptedException success) {}
1081 }
1082 });
1083 t.start();
1084 assertFalse(l.isSignalled());
1085 t.interrupt();
1086 t.join();
1087 }
1088
1089 /**
1090 * acquireSharedTimed throws IE if interrupted before released
1091 */
1092 public void testAcquireSharedNanos_InterruptedException() throws InterruptedException {
1093 final BooleanLatch l = new BooleanLatch();
1094 Thread t = new Thread(new Runnable() {
1095 public void run() {
1096 try {
1097 threadAssertFalse(l.isSignalled());
1098 l.tryAcquireSharedNanos(0, SMALL_DELAY_MS* 1000 * 1000);
1099 threadShouldThrow();
1100 } catch (InterruptedException success) {}
1101 }
1102 });
1103 t.start();
1104 Thread.sleep(SHORT_DELAY_MS);
1105 assertFalse(l.isSignalled());
1106 t.interrupt();
1107 t.join();
1108 }
1109
1110 /**
1111 * acquireSharedTimed times out if not released before timeout
1112 */
1113 public void testAcquireSharedNanos_Timeout() throws InterruptedException {
1114 final BooleanLatch l = new BooleanLatch();
1115 Thread t = new Thread(new Runnable() {
1116 public void run() {
1117 try {
1118 threadAssertFalse(l.isSignalled());
1119 threadAssertFalse(l.tryAcquireSharedNanos(0, SMALL_DELAY_MS* 1000 * 1000));
1120 } catch (InterruptedException ie) {
1121 threadUnexpectedException();
1122 }
1123 }
1124 });
1125 t.start();
1126 Thread.sleep(SHORT_DELAY_MS);
1127 assertFalse(l.isSignalled());
1128 t.join();
1129 }
1130
1131
1132 }