ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/test/tck/ForkJoinTaskTest.java
Revision: 1.17
Committed: Thu Sep 16 00:52:49 2010 UTC (13 years, 7 months ago) by jsr166
Branch: MAIN
Changes since 1.16: +256 -276 lines
Log Message:
testcase hygiene: introduce CheckedRecursiveAction and CheckedRecursiveTask; eliminate almost all threadAssertXXX; use preferred junit conventions;narrow the scope of exception checking code; make sure test failures in non-junit threads produce proper stacktraces

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 */
6 import java.util.concurrent.ExecutionException;
7 import java.util.concurrent.CancellationException;
8 import java.util.concurrent.ForkJoinPool;
9 import java.util.concurrent.ForkJoinTask;
10 import java.util.concurrent.ForkJoinWorkerThread;
11 import java.util.concurrent.RecursiveAction;
12 import java.util.concurrent.TimeUnit;
13 import java.util.concurrent.atomic.AtomicIntegerFieldUpdater;
14 import java.util.HashSet;
15 import junit.framework.*;
16
17 public class ForkJoinTaskTest extends JSR166TestCase {
18
19 public static void main(String[] args) {
20 junit.textui.TestRunner.run(suite());
21 }
22
23 public static Test suite() {
24 return new TestSuite(ForkJoinTaskTest.class);
25 }
26
27 private static ForkJoinPool mainPool() {
28 return new ForkJoinPool();
29 }
30
31 private static ForkJoinPool singletonPool() {
32 return new ForkJoinPool(1);
33 }
34
35 private static ForkJoinPool asyncSingletonPool() {
36 return new ForkJoinPool(1,
37 ForkJoinPool.defaultForkJoinWorkerThreadFactory,
38 null, true);
39 }
40
41 private void testInvokeOnPool(ForkJoinPool pool, RecursiveAction a) {
42 try {
43 assertFalse(a.isDone());
44 assertFalse(a.isCompletedNormally());
45 assertFalse(a.isCompletedAbnormally());
46 assertFalse(a.isCancelled());
47 assertNull(a.getException());
48
49 assertNull(pool.invoke(a));
50
51 assertTrue(a.isDone());
52 assertTrue(a.isCompletedNormally());
53 assertFalse(a.isCompletedAbnormally());
54 assertFalse(a.isCancelled());
55 assertNull(a.getException());
56 } finally {
57 joinPool(pool);
58 }
59 }
60
61 /*
62 * Testing coverage notes:
63 *
64 * To test extension methods and overrides, most tests use
65 * BinaryAsyncAction extension class that processes joins
66 * differently than supplied Recursive forms.
67 */
68
69 static final class FJException extends RuntimeException {
70 FJException() { super(); }
71 }
72
73 static abstract class BinaryAsyncAction extends ForkJoinTask<Void> {
74 private volatile int controlState;
75
76 static final AtomicIntegerFieldUpdater<BinaryAsyncAction> controlStateUpdater =
77 AtomicIntegerFieldUpdater.newUpdater(BinaryAsyncAction.class,
78 "controlState");
79
80 private BinaryAsyncAction parent;
81
82 private BinaryAsyncAction sibling;
83
84 protected BinaryAsyncAction() {
85 }
86
87 public final Void getRawResult() { return null; }
88 protected final void setRawResult(Void mustBeNull) { }
89
90 public final void linkSubtasks(BinaryAsyncAction x, BinaryAsyncAction y) {
91 x.parent = y.parent = this;
92 x.sibling = y;
93 y.sibling = x;
94 }
95
96 protected void onComplete(BinaryAsyncAction x, BinaryAsyncAction y) {
97 }
98
99 protected boolean onException() {
100 return true;
101 }
102
103 public void linkAndForkSubtasks(BinaryAsyncAction x, BinaryAsyncAction y) {
104 linkSubtasks(x, y);
105 y.fork();
106 x.fork();
107 }
108
109 private void completeThis() {
110 super.complete(null);
111 }
112
113 private void completeThisExceptionally(Throwable ex) {
114 super.completeExceptionally(ex);
115 }
116
117 public final void complete() {
118 BinaryAsyncAction a = this;
119 for (;;) {
120 BinaryAsyncAction s = a.sibling;
121 BinaryAsyncAction p = a.parent;
122 a.sibling = null;
123 a.parent = null;
124 a.completeThis();
125 if (p == null || p.compareAndSetControlState(0, 1))
126 break;
127 try {
128 p.onComplete(a, s);
129 } catch (Throwable rex) {
130 p.completeExceptionally(rex);
131 return;
132 }
133 a = p;
134 }
135 }
136
137 public final void completeExceptionally(Throwable ex) {
138 BinaryAsyncAction a = this;
139 while (!a.isCompletedAbnormally()) {
140 a.completeThisExceptionally(ex);
141 BinaryAsyncAction s = a.sibling;
142 if (s != null)
143 s.cancel(false);
144 if (!a.onException() || (a = a.parent) == null)
145 break;
146 }
147 }
148
149 public final BinaryAsyncAction getParent() {
150 return parent;
151 }
152
153 public BinaryAsyncAction getSibling() {
154 return sibling;
155 }
156
157 public void reinitialize() {
158 parent = sibling = null;
159 super.reinitialize();
160 }
161
162 protected final int getControlState() {
163 return controlState;
164 }
165
166 protected final boolean compareAndSetControlState(int expect,
167 int update) {
168 return controlStateUpdater.compareAndSet(this, expect, update);
169 }
170
171 protected final void setControlState(int value) {
172 controlState = value;
173 }
174
175 protected final void incrementControlState() {
176 controlStateUpdater.incrementAndGet(this);
177 }
178
179 protected final void decrementControlState() {
180 controlStateUpdater.decrementAndGet(this);
181 }
182
183 }
184
185 static final class AsyncFib extends BinaryAsyncAction {
186 int number;
187 public AsyncFib(int n) {
188 this.number = n;
189 }
190
191 public final boolean exec() {
192 AsyncFib f = this;
193 int n = f.number;
194 if (n > 1) {
195 while (n > 1) {
196 AsyncFib p = f;
197 AsyncFib r = new AsyncFib(n - 2);
198 f = new AsyncFib(--n);
199 p.linkSubtasks(r, f);
200 r.fork();
201 }
202 f.number = n;
203 }
204 f.complete();
205 return false;
206 }
207
208 protected void onComplete(BinaryAsyncAction x, BinaryAsyncAction y) {
209 number = ((AsyncFib)x).number + ((AsyncFib)y).number;
210 }
211 }
212
213
214 static final class FailingAsyncFib extends BinaryAsyncAction {
215 int number;
216 public FailingAsyncFib(int n) {
217 this.number = n;
218 }
219
220 public final boolean exec() {
221 FailingAsyncFib f = this;
222 int n = f.number;
223 if (n > 1) {
224 while (n > 1) {
225 FailingAsyncFib p = f;
226 FailingAsyncFib r = new FailingAsyncFib(n - 2);
227 f = new FailingAsyncFib(--n);
228 p.linkSubtasks(r, f);
229 r.fork();
230 }
231 f.number = n;
232 }
233 f.complete();
234 return false;
235 }
236
237 protected void onComplete(BinaryAsyncAction x, BinaryAsyncAction y) {
238 completeExceptionally(new FJException());
239 }
240 }
241
242 /**
243 * invoke returns when task completes normally.
244 * isCompletedAbnormally and isCancelled return false for normally
245 * completed tasks. getRawResult of a RecursiveAction returns null;
246 */
247 public void testInvoke() {
248 RecursiveAction a = new CheckedRecursiveAction() {
249 public void realCompute() {
250 AsyncFib f = new AsyncFib(8);
251 assertNull(f.invoke());
252 assertEquals(21, f.number);
253 assertTrue(f.isDone());
254 assertFalse(f.isCancelled());
255 assertFalse(f.isCompletedAbnormally());
256 assertNull(f.getRawResult());
257 }};
258 testInvokeOnPool(mainPool(), a);
259 }
260
261 /**
262 * quietlyInvoke task returns when task completes normally.
263 * isCompletedAbnormally and isCancelled return false for normally
264 * completed tasks
265 */
266 public void testQuietlyInvoke() {
267 RecursiveAction a = new CheckedRecursiveAction() {
268 public void realCompute() {
269 AsyncFib f = new AsyncFib(8);
270 f.quietlyInvoke();
271 assertEquals(21, f.number);
272 assertTrue(f.isDone());
273 assertFalse(f.isCancelled());
274 assertFalse(f.isCompletedAbnormally());
275 assertNull(f.getRawResult());
276 }};
277 testInvokeOnPool(mainPool(), a);
278 }
279
280 /**
281 * join of a forked task returns when task completes
282 */
283 public void testForkJoin() {
284 RecursiveAction a = new CheckedRecursiveAction() {
285 public void realCompute() {
286 AsyncFib f = new AsyncFib(8);
287 assertSame(f, f.fork());
288 assertNull(f.join());
289 assertEquals(21, f.number);
290 assertTrue(f.isDone());
291 assertNull(f.getRawResult());
292 }};
293 testInvokeOnPool(mainPool(), a);
294 }
295
296 /**
297 * get of a forked task returns when task completes
298 */
299 public void testForkGet() {
300 RecursiveAction a = new CheckedRecursiveAction() {
301 public void realCompute() throws Exception {
302 AsyncFib f = new AsyncFib(8);
303 assertSame(f, f.fork());
304 assertNull(f.get());
305 assertEquals(21, f.number);
306 assertTrue(f.isDone());
307 }};
308 testInvokeOnPool(mainPool(), a);
309 }
310
311 /**
312 * timed get of a forked task returns when task completes
313 */
314 public void testForkTimedGet() {
315 RecursiveAction a = new CheckedRecursiveAction() {
316 public void realCompute() throws Exception {
317 AsyncFib f = new AsyncFib(8);
318 assertSame(f, f.fork());
319 assertNull(f.get(LONG_DELAY_MS, TimeUnit.MILLISECONDS));
320 assertEquals(21, f.number);
321 assertTrue(f.isDone());
322 }};
323 testInvokeOnPool(mainPool(), a);
324 }
325
326 /**
327 * timed get with null time unit throws NPE
328 */
329 public void testForkTimedGetNPE() {
330 RecursiveAction a = new CheckedRecursiveAction() {
331 public void realCompute() throws Exception {
332 AsyncFib f = new AsyncFib(8);
333 assertSame(f, f.fork());
334 try {
335 f.get(5L, null);
336 shouldThrow();
337 } catch (NullPointerException success) {}
338 }};
339 testInvokeOnPool(mainPool(), a);
340 }
341
342 /**
343 * quietlyJoin of a forked task returns when task completes
344 */
345 public void testForkQuietlyJoin() {
346 RecursiveAction a = new CheckedRecursiveAction() {
347 public void realCompute() {
348 AsyncFib f = new AsyncFib(8);
349 assertSame(f, f.fork());
350 f.quietlyJoin();
351 assertEquals(21, f.number);
352 assertTrue(f.isDone());
353 }};
354 testInvokeOnPool(mainPool(), a);
355 }
356
357
358 /**
359 * helpQuiesce returns when tasks are complete.
360 * getQueuedTaskCount returns 0 when quiescent
361 */
362 public void testForkHelpQuiesce() {
363 RecursiveAction a = new CheckedRecursiveAction() {
364 public void realCompute() {
365 AsyncFib f = new AsyncFib(8);
366 assertSame(f, f.fork());
367 f.helpQuiesce();
368 assertEquals(21, f.number);
369 assertTrue(f.isDone());
370 assertEquals(0, getQueuedTaskCount());
371 }};
372 testInvokeOnPool(mainPool(), a);
373 }
374
375
376 /**
377 * invoke task throws exception when task completes abnormally
378 */
379 public void testAbnormalInvoke() {
380 RecursiveAction a = new CheckedRecursiveAction() {
381 public void realCompute() {
382 FailingAsyncFib f = new FailingAsyncFib(8);
383 try {
384 f.invoke();
385 shouldThrow();
386 } catch (FJException success) {}
387 }};
388 testInvokeOnPool(mainPool(), a);
389 }
390
391 /**
392 * quietlyInvoke task returns when task completes abnormally
393 */
394 public void testAbnormalQuietlyInvoke() {
395 RecursiveAction a = new CheckedRecursiveAction() {
396 public void realCompute() {
397 FailingAsyncFib f = new FailingAsyncFib(8);
398 f.quietlyInvoke();
399 assertTrue(f.isDone());
400 }};
401 testInvokeOnPool(mainPool(), a);
402 }
403
404 /**
405 * join of a forked task throws exception when task completes abnormally
406 */
407 public void testAbnormalForkJoin() {
408 RecursiveAction a = new CheckedRecursiveAction() {
409 public void realCompute() {
410 FailingAsyncFib f = new FailingAsyncFib(8);
411 assertSame(f, f.fork());
412 try {
413 f.join();
414 shouldThrow();
415 } catch (FJException success) {}
416 }};
417 testInvokeOnPool(mainPool(), a);
418 }
419
420 /**
421 * get of a forked task throws exception when task completes abnormally
422 */
423 public void testAbnormalForkGet() {
424 RecursiveAction a = new CheckedRecursiveAction() {
425 public void realCompute() throws Exception {
426 FailingAsyncFib f = new FailingAsyncFib(8);
427 assertSame(f, f.fork());
428 try {
429 f.get();
430 shouldThrow();
431 } catch (ExecutionException success) {}
432 }};
433 testInvokeOnPool(mainPool(), a);
434 }
435
436 /**
437 * timed get of a forked task throws exception when task completes abnormally
438 */
439 public void testAbnormalForkTimedGet() {
440 RecursiveAction a = new CheckedRecursiveAction() {
441 public void realCompute() throws Exception {
442 FailingAsyncFib f = new FailingAsyncFib(8);
443 assertSame(f, f.fork());
444 try {
445 f.get(LONG_DELAY_MS, TimeUnit.MILLISECONDS);
446 shouldThrow();
447 } catch (ExecutionException success) {}
448 }};
449 testInvokeOnPool(mainPool(), a);
450 }
451
452 /**
453 * quietlyJoin of a forked task returns when task completes abnormally
454 */
455 public void testAbnormalForkQuietlyJoin() {
456 RecursiveAction a = new CheckedRecursiveAction() {
457 public void realCompute() {
458 FailingAsyncFib f = new FailingAsyncFib(8);
459 assertSame(f, f.fork());
460 f.quietlyJoin();
461 assertTrue(f.isDone());
462 assertTrue(f.isCompletedAbnormally());
463 assertTrue(f.getException() instanceof FJException);
464 }};
465 testInvokeOnPool(mainPool(), a);
466 }
467
468 /**
469 * invoke task throws exception when task cancelled
470 */
471 public void testCancelledInvoke() {
472 RecursiveAction a = new CheckedRecursiveAction() {
473 public void realCompute() {
474 AsyncFib f = new AsyncFib(8);
475 assertTrue(f.cancel(true));
476 try {
477 f.invoke();
478 shouldThrow();
479 } catch (CancellationException success) {}
480 }};
481 testInvokeOnPool(mainPool(), a);
482 }
483
484 /**
485 * join of a forked task throws exception when task cancelled
486 */
487 public void testCancelledForkJoin() {
488 RecursiveAction a = new CheckedRecursiveAction() {
489 public void realCompute() {
490 AsyncFib f = new AsyncFib(8);
491 assertTrue(f.cancel(true));
492 assertSame(f, f.fork());
493 try {
494 f.join();
495 shouldThrow();
496 } catch (CancellationException success) {}
497 }};
498 testInvokeOnPool(mainPool(), a);
499 }
500
501 /**
502 * get of a forked task throws exception when task cancelled
503 */
504 public void testCancelledForkGet() {
505 RecursiveAction a = new CheckedRecursiveAction() {
506 public void realCompute() throws Exception {
507 AsyncFib f = new AsyncFib(8);
508 assertTrue(f.cancel(true));
509 assertSame(f, f.fork());
510 try {
511 f.get();
512 shouldThrow();
513 } catch (CancellationException success) {}
514 }};
515 testInvokeOnPool(mainPool(), a);
516 }
517
518 /**
519 * timed get of a forked task throws exception when task cancelled
520 */
521 public void testCancelledForkTimedGet() throws Exception {
522 RecursiveAction a = new CheckedRecursiveAction() {
523 public void realCompute() throws Exception {
524 AsyncFib f = new AsyncFib(8);
525 assertTrue(f.cancel(true));
526 assertSame(f, f.fork());
527 try {
528 f.get(LONG_DELAY_MS, TimeUnit.MILLISECONDS);
529 shouldThrow();
530 } catch (CancellationException success) {}
531 }};
532 testInvokeOnPool(mainPool(), a);
533 }
534
535 /**
536 * quietlyJoin of a forked task returns when task cancelled
537 */
538 public void testCancelledForkQuietlyJoin() {
539 RecursiveAction a = new CheckedRecursiveAction() {
540 public void realCompute() {
541 AsyncFib f = new AsyncFib(8);
542 assertTrue(f.cancel(true));
543 assertSame(f, f.fork());
544 f.quietlyJoin();
545 assertTrue(f.isDone());
546 assertTrue(f.isCompletedAbnormally());
547 assertTrue(f.isCancelled());
548 assertTrue(f.getException() instanceof CancellationException);
549 }};
550 testInvokeOnPool(mainPool(), a);
551 }
552
553 /**
554 * getPool of executing task returns its pool
555 */
556 public void testGetPool() {
557 final ForkJoinPool mainPool = mainPool();
558 RecursiveAction a = new CheckedRecursiveAction() {
559 public void realCompute() {
560 assertSame(mainPool, getPool());
561 }};
562 testInvokeOnPool(mainPool, a);
563 }
564
565 /**
566 * getPool of non-FJ task returns null
567 */
568 public void testGetPool2() {
569 RecursiveAction a = new CheckedRecursiveAction() {
570 public void realCompute() {
571 assertNull(getPool());
572 }};
573 assertNull(a.invoke());
574 }
575
576 /**
577 * inForkJoinPool of executing task returns true
578 */
579 public void testInForkJoinPool() {
580 RecursiveAction a = new CheckedRecursiveAction() {
581 public void realCompute() {
582 assertTrue(inForkJoinPool());
583 }};
584 testInvokeOnPool(mainPool(), a);
585 }
586
587 /**
588 * inForkJoinPool of non-FJ task returns false
589 */
590 public void testInForkJoinPool2() {
591 RecursiveAction a = new CheckedRecursiveAction() {
592 public void realCompute() {
593 assertTrue(!inForkJoinPool());
594 }};
595 assertNull(a.invoke());
596 }
597
598 /**
599 * setRawResult(null) succeeds
600 */
601 public void testSetRawResult() {
602 RecursiveAction a = new CheckedRecursiveAction() {
603 public void realCompute() {
604 setRawResult(null);
605 }};
606 assertNull(a.invoke());
607 }
608
609 /**
610 * invoke task throws exception after invoking completeExceptionally
611 */
612 public void testCompleteExceptionally() {
613 RecursiveAction a = new CheckedRecursiveAction() {
614 public void realCompute() {
615 AsyncFib f = new AsyncFib(8);
616 f.completeExceptionally(new FJException());
617 try {
618 f.invoke();
619 shouldThrow();
620 } catch (FJException success) {}
621 }};
622 testInvokeOnPool(mainPool(), a);
623 }
624
625 /**
626 * invokeAll(t1, t2) invokes all task arguments
627 */
628 public void testInvokeAll2() {
629 RecursiveAction a = new CheckedRecursiveAction() {
630 public void realCompute() {
631 AsyncFib f = new AsyncFib(8);
632 AsyncFib g = new AsyncFib(9);
633 invokeAll(f, g);
634 assertTrue(f.isDone());
635 assertEquals(21, f.number);
636 assertTrue(g.isDone());
637 assertEquals(34, g.number);
638 }};
639 testInvokeOnPool(mainPool(), a);
640 }
641
642 /**
643 * invokeAll(tasks) with 1 argument invokes task
644 */
645 public void testInvokeAll1() {
646 RecursiveAction a = new CheckedRecursiveAction() {
647 public void realCompute() {
648 AsyncFib f = new AsyncFib(8);
649 invokeAll(f);
650 assertTrue(f.isDone());
651 assertEquals(21, f.number);
652 }};
653 testInvokeOnPool(mainPool(), a);
654 }
655
656 /**
657 * invokeAll(tasks) with > 2 argument invokes tasks
658 */
659 public void testInvokeAll3() {
660 RecursiveAction a = new CheckedRecursiveAction() {
661 public void realCompute() {
662 AsyncFib f = new AsyncFib(8);
663 AsyncFib g = new AsyncFib(9);
664 AsyncFib h = new AsyncFib(7);
665 invokeAll(f, g, h);
666 assertTrue(f.isDone());
667 assertEquals(21, f.number);
668 assertTrue(g.isDone());
669 assertEquals(34, g.number);
670 assertTrue(h.isDone());
671 assertEquals(13, h.number);
672 }};
673 testInvokeOnPool(mainPool(), a);
674 }
675
676 /**
677 * invokeAll(collection) invokes all tasks in the collection
678 */
679 public void testInvokeAllCollection() {
680 RecursiveAction a = new CheckedRecursiveAction() {
681 public void realCompute() {
682 AsyncFib f = new AsyncFib(8);
683 AsyncFib g = new AsyncFib(9);
684 AsyncFib h = new AsyncFib(7);
685 HashSet set = new HashSet();
686 set.add(f);
687 set.add(g);
688 set.add(h);
689 invokeAll(set);
690 assertTrue(f.isDone());
691 assertEquals(21, f.number);
692 assertTrue(g.isDone());
693 assertEquals(34, g.number);
694 assertTrue(h.isDone());
695 assertEquals(13, h.number);
696 }};
697 testInvokeOnPool(mainPool(), a);
698 }
699
700
701 /**
702 * invokeAll(tasks) with any null task throws NPE
703 */
704 public void testInvokeAllNPE() {
705 RecursiveAction a = new CheckedRecursiveAction() {
706 public void realCompute() {
707 AsyncFib f = new AsyncFib(8);
708 AsyncFib g = new AsyncFib(9);
709 AsyncFib h = null;
710 try {
711 invokeAll(f, g, h);
712 shouldThrow();
713 } catch (NullPointerException success) {}
714 }};
715 testInvokeOnPool(mainPool(), a);
716 }
717
718 /**
719 * invokeAll(t1, t2) throw exception if any task does
720 */
721 public void testAbnormalInvokeAll2() {
722 RecursiveAction a = new CheckedRecursiveAction() {
723 public void realCompute() {
724 AsyncFib f = new AsyncFib(8);
725 FailingAsyncFib g = new FailingAsyncFib(9);
726 try {
727 invokeAll(f, g);
728 shouldThrow();
729 } catch (FJException success) {}
730 }};
731 testInvokeOnPool(mainPool(), a);
732 }
733
734 /**
735 * invokeAll(tasks) with 1 argument throws exception if task does
736 */
737 public void testAbnormalInvokeAll1() {
738 RecursiveAction a = new CheckedRecursiveAction() {
739 public void realCompute() {
740 FailingAsyncFib g = new FailingAsyncFib(9);
741 try {
742 invokeAll(g);
743 shouldThrow();
744 } catch (FJException success) {}
745 }};
746 testInvokeOnPool(mainPool(), a);
747 }
748
749 /**
750 * invokeAll(tasks) with > 2 argument throws exception if any task does
751 */
752 public void testAbnormalInvokeAll3() {
753 RecursiveAction a = new CheckedRecursiveAction() {
754 public void realCompute() {
755 AsyncFib f = new AsyncFib(8);
756 FailingAsyncFib g = new FailingAsyncFib(9);
757 AsyncFib h = new AsyncFib(7);
758 try {
759 invokeAll(f, g, h);
760 shouldThrow();
761 } catch (FJException success) {}
762 }};
763 testInvokeOnPool(mainPool(), a);
764 }
765
766 /**
767 * invokeAll(collection) throws exception if any task does
768 */
769 public void testAbnormalInvokeAllCollection() {
770 RecursiveAction a = new CheckedRecursiveAction() {
771 public void realCompute() {
772 FailingAsyncFib f = new FailingAsyncFib(8);
773 AsyncFib g = new AsyncFib(9);
774 AsyncFib h = new AsyncFib(7);
775 HashSet set = new HashSet();
776 set.add(f);
777 set.add(g);
778 set.add(h);
779 try {
780 invokeAll(set);
781 shouldThrow();
782 } catch (FJException success) {}
783 }};
784 testInvokeOnPool(mainPool(), a);
785 }
786
787 /**
788 * tryUnfork returns true for most recent unexecuted task,
789 * and suppresses execution
790 */
791 public void testTryUnfork() {
792 RecursiveAction a = new CheckedRecursiveAction() {
793 public void realCompute() {
794 AsyncFib g = new AsyncFib(9);
795 assertSame(g, g.fork());
796 AsyncFib f = new AsyncFib(8);
797 assertSame(f, f.fork());
798 assertTrue(f.tryUnfork());
799 helpQuiesce();
800 assertFalse(f.isDone());
801 assertTrue(g.isDone());
802 }};
803 testInvokeOnPool(singletonPool(), a);
804 }
805
806 /**
807 * getSurplusQueuedTaskCount returns > 0 when
808 * there are more tasks than threads
809 */
810 public void testGetSurplusQueuedTaskCount() {
811 RecursiveAction a = new CheckedRecursiveAction() {
812 public void realCompute() {
813 AsyncFib h = new AsyncFib(7);
814 assertSame(h, h.fork());
815 AsyncFib g = new AsyncFib(9);
816 assertSame(g, g.fork());
817 AsyncFib f = new AsyncFib(8);
818 assertSame(f, f.fork());
819 assertTrue(getSurplusQueuedTaskCount() > 0);
820 helpQuiesce();
821 }};
822 testInvokeOnPool(singletonPool(), a);
823 }
824
825 /**
826 * peekNextLocalTask returns most recent unexecuted task.
827 */
828 public void testPeekNextLocalTask() {
829 RecursiveAction a = new CheckedRecursiveAction() {
830 public void realCompute() {
831 AsyncFib g = new AsyncFib(9);
832 assertSame(g, g.fork());
833 AsyncFib f = new AsyncFib(8);
834 assertSame(f, f.fork());
835 assertSame(f, peekNextLocalTask());
836 assertNull(f.join());
837 assertTrue(f.isDone());
838 helpQuiesce();
839 }};
840 testInvokeOnPool(singletonPool(), a);
841 }
842
843 /**
844 * pollNextLocalTask returns most recent unexecuted task
845 * without executing it
846 */
847 public void testPollNextLocalTask() {
848 RecursiveAction a = new CheckedRecursiveAction() {
849 public void realCompute() {
850 AsyncFib g = new AsyncFib(9);
851 assertSame(g, g.fork());
852 AsyncFib f = new AsyncFib(8);
853 assertSame(f, f.fork());
854 assertSame(f, pollNextLocalTask());
855 helpQuiesce();
856 assertFalse(f.isDone());
857 }};
858 testInvokeOnPool(singletonPool(), a);
859 }
860
861 /**
862 * pollTask returns an unexecuted task
863 * without executing it
864 */
865 public void testPollTask() {
866 RecursiveAction a = new CheckedRecursiveAction() {
867 public void realCompute() {
868 AsyncFib g = new AsyncFib(9);
869 assertSame(g, g.fork());
870 AsyncFib f = new AsyncFib(8);
871 assertSame(f, f.fork());
872 assertSame(f, pollTask());
873 helpQuiesce();
874 assertFalse(f.isDone());
875 assertTrue(g.isDone());
876 }};
877 testInvokeOnPool(singletonPool(), a);
878 }
879
880 /**
881 * peekNextLocalTask returns least recent unexecuted task in async mode
882 */
883 public void testPeekNextLocalTaskAsync() {
884 RecursiveAction a = new CheckedRecursiveAction() {
885 public void realCompute() {
886 AsyncFib g = new AsyncFib(9);
887 assertSame(g, g.fork());
888 AsyncFib f = new AsyncFib(8);
889 assertSame(f, f.fork());
890 assertSame(g, peekNextLocalTask());
891 assertNull(f.join());
892 helpQuiesce();
893 assertTrue(f.isDone());
894 }};
895 testInvokeOnPool(asyncSingletonPool(), a);
896 }
897
898 /**
899 * pollNextLocalTask returns least recent unexecuted task
900 * without executing it, in async mode
901 */
902 public void testPollNextLocalTaskAsync() {
903 RecursiveAction a = new CheckedRecursiveAction() {
904 public void realCompute() {
905 AsyncFib g = new AsyncFib(9);
906 assertSame(g, g.fork());
907 AsyncFib f = new AsyncFib(8);
908 assertSame(f, f.fork());
909 assertSame(g, pollNextLocalTask());
910 helpQuiesce();
911 assertTrue(f.isDone());
912 assertFalse(g.isDone());
913 }};
914 testInvokeOnPool(asyncSingletonPool(), a);
915 }
916
917 /**
918 * pollTask returns an unexecuted task
919 * without executing it, in async mode
920 */
921 public void testPollTaskAsync() {
922 RecursiveAction a = new CheckedRecursiveAction() {
923 public void realCompute() {
924 AsyncFib g = new AsyncFib(9);
925 assertSame(g, g.fork());
926 AsyncFib f = new AsyncFib(8);
927 assertSame(f, f.fork());
928 assertSame(g, pollTask());
929 helpQuiesce();
930 assertTrue(f.isDone());
931 assertFalse(g.isDone());
932 }};
933 testInvokeOnPool(asyncSingletonPool(), a);
934 }
935 }