• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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/publicdomain/zero/1.0/
5  */
6 
7 package jsr166;
8 
9 import static java.util.concurrent.TimeUnit.MILLISECONDS;
10 import static java.util.concurrent.TimeUnit.NANOSECONDS;
11 
12 import java.security.PrivilegedAction;
13 import java.security.PrivilegedExceptionAction;
14 import java.util.ArrayList;
15 import java.util.Collection;
16 import java.util.List;
17 import java.util.concurrent.Callable;
18 import java.util.concurrent.CountDownLatch;
19 import java.util.concurrent.ExecutionException;
20 import java.util.concurrent.Executors;
21 import java.util.concurrent.ExecutorService;
22 import java.util.concurrent.ForkJoinPool;
23 import java.util.concurrent.ForkJoinTask;
24 import java.util.concurrent.ForkJoinWorkerThread;
25 import java.util.concurrent.Future;
26 import java.util.concurrent.RecursiveTask;
27 import java.util.concurrent.RejectedExecutionException;
28 import java.util.concurrent.atomic.AtomicBoolean;
29 import java.util.concurrent.locks.ReentrantLock;
30 
31 import junit.framework.AssertionFailedError;
32 import junit.framework.Test;
33 import junit.framework.TestSuite;
34 
35 public class ForkJoinPoolTest extends JSR166TestCase {
36     // android-note: Removed because the CTS runner does a bad job of
37     // retrying tests that have suite() declarations.
38     //
39     // public static void main(String[] args) {
40     //     main(suite(), args);
41     // }
42     // public static Test suite() {
43     //     return new TestSuite(...);
44     // }
45 
46     /*
47      * Testing coverage notes:
48      *
49      * 1. shutdown and related methods are tested via super.joinPool.
50      *
51      * 2. newTaskFor and adapters are tested in submit/invoke tests
52      *
53      * 3. We cannot portably test monitoring methods such as
54      * getStealCount() since they rely ultimately on random task
55      * stealing that may cause tasks not to be stolen/propagated
56      * across threads, especially on uniprocessors.
57      *
58      * 4. There are no independently testable ForkJoinWorkerThread
59      * methods, but they are covered here and in task tests.
60      */
61 
62     // Some classes to test extension and factory methods
63 
64     static class MyHandler implements Thread.UncaughtExceptionHandler {
65         volatile int catches = 0;
uncaughtException(Thread t, Throwable e)66         public void uncaughtException(Thread t, Throwable e) {
67             ++catches;
68         }
69     }
70 
71     // to test handlers
72     static class FailingFJWSubclass extends ForkJoinWorkerThread {
FailingFJWSubclass(ForkJoinPool p)73         public FailingFJWSubclass(ForkJoinPool p) { super(p) ; }
onStart()74         protected void onStart() { super.onStart(); throw new Error(); }
75     }
76 
77     static class FailingThreadFactory
78             implements ForkJoinPool.ForkJoinWorkerThreadFactory {
79         volatile int calls = 0;
newThread(ForkJoinPool p)80         public ForkJoinWorkerThread newThread(ForkJoinPool p) {
81             if (++calls > 1) return null;
82             return new FailingFJWSubclass(p);
83         }
84     }
85 
86     static class SubFJP extends ForkJoinPool { // to expose protected
SubFJP()87         SubFJP() { super(1); }
drainTasksTo(Collection<? super ForkJoinTask<?>> c)88         public int drainTasksTo(Collection<? super ForkJoinTask<?>> c) {
89             return super.drainTasksTo(c);
90         }
pollSubmission()91         public ForkJoinTask<?> pollSubmission() {
92             return super.pollSubmission();
93         }
94     }
95 
96     static class ManagedLocker implements ForkJoinPool.ManagedBlocker {
97         final ReentrantLock lock;
98         boolean hasLock = false;
ManagedLocker(ReentrantLock lock)99         ManagedLocker(ReentrantLock lock) { this.lock = lock; }
block()100         public boolean block() {
101             if (!hasLock)
102                 lock.lock();
103             return true;
104         }
isReleasable()105         public boolean isReleasable() {
106             return hasLock || (hasLock = lock.tryLock());
107         }
108     }
109 
110     // A simple recursive task for testing
111     static final class FibTask extends RecursiveTask<Integer> {
112         final int number;
FibTask(int n)113         FibTask(int n) { number = n; }
compute()114         protected Integer compute() {
115             int n = number;
116             if (n <= 1)
117                 return n;
118             FibTask f1 = new FibTask(n - 1);
119             f1.fork();
120             return (new FibTask(n - 2)).compute() + f1.join();
121         }
122     }
123 
124     // A failing task for testing
125     static final class FailingTask extends ForkJoinTask<Void> {
getRawResult()126         public final Void getRawResult() { return null; }
setRawResult(Void mustBeNull)127         protected final void setRawResult(Void mustBeNull) { }
exec()128         protected final boolean exec() { throw new Error(); }
FailingTask()129         FailingTask() {}
130     }
131 
132     // Fib needlessly using locking to test ManagedBlockers
133     static final class LockingFibTask extends RecursiveTask<Integer> {
134         final int number;
135         final ManagedLocker locker;
136         final ReentrantLock lock;
LockingFibTask(int n, ManagedLocker locker, ReentrantLock lock)137         LockingFibTask(int n, ManagedLocker locker, ReentrantLock lock) {
138             number = n;
139             this.locker = locker;
140             this.lock = lock;
141         }
compute()142         protected Integer compute() {
143             int n;
144             LockingFibTask f1 = null;
145             LockingFibTask f2 = null;
146             locker.block();
147             n = number;
148             if (n > 1) {
149                 f1 = new LockingFibTask(n - 1, locker, lock);
150                 f2 = new LockingFibTask(n - 2, locker, lock);
151             }
152             lock.unlock();
153             if (n <= 1)
154                 return n;
155             else {
156                 f1.fork();
157                 return f2.compute() + f1.join();
158             }
159         }
160     }
161 
162     /**
163      * Successfully constructed pool reports default factory,
164      * parallelism and async mode policies, no active threads or
165      * tasks, and quiescent running state.
166      */
testDefaultInitialState()167     public void testDefaultInitialState() {
168         ForkJoinPool p = new ForkJoinPool(1);
169         try {
170             assertSame(ForkJoinPool.defaultForkJoinWorkerThreadFactory,
171                        p.getFactory());
172             assertFalse(p.getAsyncMode());
173             assertEquals(0, p.getActiveThreadCount());
174             assertEquals(0, p.getStealCount());
175             assertEquals(0, p.getQueuedTaskCount());
176             assertEquals(0, p.getQueuedSubmissionCount());
177             assertFalse(p.hasQueuedSubmissions());
178             assertFalse(p.isShutdown());
179             assertFalse(p.isTerminating());
180             assertFalse(p.isTerminated());
181         } finally {
182             joinPool(p);
183         }
184     }
185 
186     /**
187      * Constructor throws if size argument is less than zero
188      */
testConstructor1()189     public void testConstructor1() {
190         try {
191             new ForkJoinPool(-1);
192             shouldThrow();
193         } catch (IllegalArgumentException success) {}
194     }
195 
196     /**
197      * Constructor throws if factory argument is null
198      */
testConstructor2()199     public void testConstructor2() {
200         try {
201             new ForkJoinPool(1, null, null, false);
202             shouldThrow();
203         } catch (NullPointerException success) {}
204     }
205 
206     /**
207      * getParallelism returns size set in constructor
208      */
testGetParallelism()209     public void testGetParallelism() {
210         ForkJoinPool p = new ForkJoinPool(1);
211         try {
212             assertEquals(1, p.getParallelism());
213         } finally {
214             joinPool(p);
215         }
216     }
217 
218     /**
219      * getPoolSize returns number of started workers.
220      */
testGetPoolSize()221     public void testGetPoolSize() {
222         ForkJoinPool p = new ForkJoinPool(1);
223         try {
224             assertEquals(0, p.getActiveThreadCount());
225             Future<String> future = p.submit(new StringTask());
226             assertEquals(1, p.getPoolSize());
227         } finally {
228             joinPool(p);
229         }
230     }
231 
232     /**
233      * awaitTermination on a non-shutdown pool times out
234      */
testAwaitTermination_timesOut()235     public void testAwaitTermination_timesOut() throws InterruptedException {
236         ForkJoinPool p = new ForkJoinPool(1);
237         assertFalse(p.isTerminated());
238         assertFalse(p.awaitTermination(Long.MIN_VALUE, NANOSECONDS));
239         assertFalse(p.awaitTermination(Long.MIN_VALUE, MILLISECONDS));
240         assertFalse(p.awaitTermination(-1L, NANOSECONDS));
241         assertFalse(p.awaitTermination(-1L, MILLISECONDS));
242         assertFalse(p.awaitTermination(0L, NANOSECONDS));
243         assertFalse(p.awaitTermination(0L, MILLISECONDS));
244         long timeoutNanos = 999999L;
245         long startTime = System.nanoTime();
246         assertFalse(p.awaitTermination(timeoutNanos, NANOSECONDS));
247         assertTrue(System.nanoTime() - startTime >= timeoutNanos);
248         assertFalse(p.isTerminated());
249         startTime = System.nanoTime();
250         long timeoutMillis = timeoutMillis();
251         assertFalse(p.awaitTermination(timeoutMillis, MILLISECONDS));
252         assertTrue(millisElapsedSince(startTime) >= timeoutMillis);
253         assertFalse(p.isTerminated());
254         p.shutdown();
255         assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
256         assertTrue(p.isTerminated());
257     }
258 
259     /**
260      * setUncaughtExceptionHandler changes handler for uncaught exceptions.
261      *
262      * Additionally tests: Overriding ForkJoinWorkerThread.onStart
263      * performs its defined action
264      */
testSetUncaughtExceptionHandler()265     public void testSetUncaughtExceptionHandler() throws InterruptedException {
266         final CountDownLatch uehInvoked = new CountDownLatch(1);
267         final Thread.UncaughtExceptionHandler eh =
268             new Thread.UncaughtExceptionHandler() {
269                 public void uncaughtException(Thread t, Throwable e) {
270                     uehInvoked.countDown();
271                 }};
272         ForkJoinPool p = new ForkJoinPool(1, new FailingThreadFactory(),
273                                           eh, false);
274         try {
275             assertSame(eh, p.getUncaughtExceptionHandler());
276             try {
277                 p.execute(new FibTask(8));
278                 assertTrue(uehInvoked.await(MEDIUM_DELAY_MS, MILLISECONDS));
279             } catch (RejectedExecutionException ok) {
280             }
281         } finally {
282             p.shutdownNow(); // failure might have prevented processing task
283             joinPool(p);
284         }
285     }
286 
287     /**
288      * After invoking a single task, isQuiescent eventually becomes
289      * true, at which time queues are empty, threads are not active,
290      * the task has completed successfully, and construction
291      * parameters continue to hold
292      */
testIsQuiescent()293     public void testIsQuiescent() throws Exception {
294         ForkJoinPool p = new ForkJoinPool(2);
295         try {
296             assertTrue(p.isQuiescent());
297             long startTime = System.nanoTime();
298             FibTask f = new FibTask(20);
299             p.invoke(f);
300             assertSame(ForkJoinPool.defaultForkJoinWorkerThreadFactory,
301                        p.getFactory());
302             while (! p.isQuiescent()) {
303                 if (millisElapsedSince(startTime) > LONG_DELAY_MS)
304                     throw new AssertionFailedError("timed out");
305                 assertFalse(p.getAsyncMode());
306                 assertFalse(p.isShutdown());
307                 assertFalse(p.isTerminating());
308                 assertFalse(p.isTerminated());
309                 Thread.yield();
310             }
311 
312             assertTrue(p.isQuiescent());
313             assertFalse(p.getAsyncMode());
314             assertEquals(0, p.getActiveThreadCount());
315             assertEquals(0, p.getQueuedTaskCount());
316             assertEquals(0, p.getQueuedSubmissionCount());
317             assertFalse(p.hasQueuedSubmissions());
318             assertFalse(p.isShutdown());
319             assertFalse(p.isTerminating());
320             assertFalse(p.isTerminated());
321             assertTrue(f.isDone());
322             assertEquals(6765, (int) f.get());
323         } finally {
324             joinPool(p);
325         }
326     }
327 
328     /**
329      * Completed submit(ForkJoinTask) returns result
330      */
testSubmitForkJoinTask()331     public void testSubmitForkJoinTask() throws Throwable {
332         ForkJoinPool p = new ForkJoinPool(1);
333         try {
334             ForkJoinTask<Integer> f = p.submit(new FibTask(8));
335             assertEquals(21, (int) f.get());
336         } finally {
337             joinPool(p);
338         }
339     }
340 
341     /**
342      * A task submitted after shutdown is rejected
343      */
testSubmitAfterShutdown()344     public void testSubmitAfterShutdown() {
345         ForkJoinPool p = new ForkJoinPool(1);
346         try {
347             p.shutdown();
348             assertTrue(p.isShutdown());
349             try {
350                 ForkJoinTask<Integer> f = p.submit(new FibTask(8));
351                 shouldThrow();
352             } catch (RejectedExecutionException success) {}
353         } finally {
354             joinPool(p);
355         }
356     }
357 
358     /**
359      * Pool maintains parallelism when using ManagedBlocker
360      */
testBlockingForkJoinTask()361     public void testBlockingForkJoinTask() throws Throwable {
362         ForkJoinPool p = new ForkJoinPool(4);
363         try {
364             ReentrantLock lock = new ReentrantLock();
365             ManagedLocker locker = new ManagedLocker(lock);
366             ForkJoinTask<Integer> f = new LockingFibTask(20, locker, lock);
367             p.execute(f);
368             assertEquals(6765, (int) f.get());
369         } finally {
370             p.shutdownNow(); // don't wait out shutdown
371         }
372     }
373 
374     /**
375      * pollSubmission returns unexecuted submitted task, if present
376      */
testPollSubmission()377     public void testPollSubmission() {
378         final CountDownLatch done = new CountDownLatch(1);
379         SubFJP p = new SubFJP();
380         try {
381             ForkJoinTask a = p.submit(awaiter(done));
382             ForkJoinTask b = p.submit(awaiter(done));
383             ForkJoinTask c = p.submit(awaiter(done));
384             ForkJoinTask r = p.pollSubmission();
385             assertTrue(r == a || r == b || r == c);
386             assertFalse(r.isDone());
387         } finally {
388             done.countDown();
389             joinPool(p);
390         }
391     }
392 
393     /**
394      * drainTasksTo transfers unexecuted submitted tasks, if present
395      */
testDrainTasksTo()396     public void testDrainTasksTo() {
397         final CountDownLatch done = new CountDownLatch(1);
398         SubFJP p = new SubFJP();
399         try {
400             ForkJoinTask a = p.submit(awaiter(done));
401             ForkJoinTask b = p.submit(awaiter(done));
402             ForkJoinTask c = p.submit(awaiter(done));
403             ArrayList<ForkJoinTask> al = new ArrayList();
404             p.drainTasksTo(al);
405             assertTrue(al.size() > 0);
406             for (ForkJoinTask r : al) {
407                 assertTrue(r == a || r == b || r == c);
408                 assertFalse(r.isDone());
409             }
410         } finally {
411             done.countDown();
412             joinPool(p);
413         }
414     }
415 
416     // FJ Versions of AbstractExecutorService tests
417 
418     /**
419      * execute(runnable) runs it to completion
420      */
testExecuteRunnable()421     public void testExecuteRunnable() throws Throwable {
422         ExecutorService e = new ForkJoinPool(1);
423         try {
424             final AtomicBoolean done = new AtomicBoolean(false);
425             Future<?> future = e.submit(new CheckedRunnable() {
426                 public void realRun() {
427                     done.set(true);
428                 }});
429             assertNull(future.get());
430             assertNull(future.get(0, MILLISECONDS));
431             assertTrue(done.get());
432             assertTrue(future.isDone());
433             assertFalse(future.isCancelled());
434         } finally {
435             joinPool(e);
436         }
437     }
438 
439     /**
440      * Completed submit(callable) returns result
441      */
testSubmitCallable()442     public void testSubmitCallable() throws Throwable {
443         ExecutorService e = new ForkJoinPool(1);
444         try {
445             Future<String> future = e.submit(new StringTask());
446             assertSame(TEST_STRING, future.get());
447             assertTrue(future.isDone());
448             assertFalse(future.isCancelled());
449         } finally {
450             joinPool(e);
451         }
452     }
453 
454     /**
455      * Completed submit(runnable) returns successfully
456      */
testSubmitRunnable()457     public void testSubmitRunnable() throws Throwable {
458         ExecutorService e = new ForkJoinPool(1);
459         try {
460             Future<?> future = e.submit(new NoOpRunnable());
461             assertNull(future.get());
462             assertTrue(future.isDone());
463             assertFalse(future.isCancelled());
464         } finally {
465             joinPool(e);
466         }
467     }
468 
469     /**
470      * Completed submit(runnable, result) returns result
471      */
testSubmitRunnable2()472     public void testSubmitRunnable2() throws Throwable {
473         ExecutorService e = new ForkJoinPool(1);
474         try {
475             Future<String> future = e.submit(new NoOpRunnable(), TEST_STRING);
476             assertSame(TEST_STRING, future.get());
477             assertTrue(future.isDone());
478             assertFalse(future.isCancelled());
479         } finally {
480             joinPool(e);
481         }
482     }
483 
484     /**
485      * A submitted privileged action runs to completion
486      */
testSubmitPrivilegedAction()487     public void testSubmitPrivilegedAction() throws Exception {
488         final Callable callable = Executors.callable(new PrivilegedAction() {
489                 public Object run() { return TEST_STRING; }});
490         Runnable r = new CheckedRunnable() {
491         public void realRun() throws Exception {
492             ExecutorService e = new ForkJoinPool(1);
493             try {
494                 Future future = e.submit(callable);
495                 assertSame(TEST_STRING, future.get());
496             } finally {
497                 joinPool(e);
498             }
499         }};
500 
501         runWithPermissions(r, new RuntimePermission("modifyThread"));
502     }
503 
504     /**
505      * A submitted privileged exception action runs to completion
506      */
testSubmitPrivilegedExceptionAction()507     public void testSubmitPrivilegedExceptionAction() throws Exception {
508         final Callable callable =
509             Executors.callable(new PrivilegedExceptionAction() {
510                 public Object run() { return TEST_STRING; }});
511         Runnable r = new CheckedRunnable() {
512         public void realRun() throws Exception {
513             ExecutorService e = new ForkJoinPool(1);
514             try {
515                 Future future = e.submit(callable);
516                 assertSame(TEST_STRING, future.get());
517             } finally {
518                 joinPool(e);
519             }
520         }};
521 
522         runWithPermissions(r, new RuntimePermission("modifyThread"));
523     }
524 
525     /**
526      * A submitted failed privileged exception action reports exception
527      */
testSubmitFailedPrivilegedExceptionAction()528     public void testSubmitFailedPrivilegedExceptionAction() throws Exception {
529         final Callable callable =
530             Executors.callable(new PrivilegedExceptionAction() {
531                 public Object run() { throw new IndexOutOfBoundsException(); }});
532         Runnable r = new CheckedRunnable() {
533         public void realRun() throws Exception {
534             ExecutorService e = new ForkJoinPool(1);
535             try {
536                 Future future = e.submit(callable);
537                 try {
538                     future.get();
539                     shouldThrow();
540                 } catch (ExecutionException success) {
541                     assertTrue(success.getCause() instanceof IndexOutOfBoundsException);
542                 }
543             } finally {
544                 joinPool(e);
545             }
546         }};
547 
548         runWithPermissions(r, new RuntimePermission("modifyThread"));
549     }
550 
551     /**
552      * execute(null runnable) throws NullPointerException
553      */
testExecuteNullRunnable()554     public void testExecuteNullRunnable() {
555         ExecutorService e = new ForkJoinPool(1);
556         try {
557             Future<?> future = e.submit((Runnable) null);
558             shouldThrow();
559         } catch (NullPointerException success) {
560         } finally {
561             joinPool(e);
562         }
563     }
564 
565     /**
566      * submit(null callable) throws NullPointerException
567      */
testSubmitNullCallable()568     public void testSubmitNullCallable() {
569         ExecutorService e = new ForkJoinPool(1);
570         try {
571             Future<String> future = e.submit((Callable) null);
572             shouldThrow();
573         } catch (NullPointerException success) {
574         } finally {
575             joinPool(e);
576         }
577     }
578 
579     /**
580      * submit(callable).get() throws InterruptedException if interrupted
581      */
testInterruptedSubmit()582     public void testInterruptedSubmit() throws InterruptedException {
583         final CountDownLatch submitted    = new CountDownLatch(1);
584         final CountDownLatch quittingTime = new CountDownLatch(1);
585         final ExecutorService p = new ForkJoinPool(1);
586         final Callable<Void> awaiter = new CheckedCallable<Void>() {
587             public Void realCall() throws InterruptedException {
588                 assertTrue(quittingTime.await(MEDIUM_DELAY_MS, MILLISECONDS));
589                 return null;
590             }};
591         try {
592             Thread t = new Thread(new CheckedInterruptedRunnable() {
593                 public void realRun() throws Exception {
594                     Future<Void> future = p.submit(awaiter);
595                     submitted.countDown();
596                     future.get();
597                 }});
598             t.start();
599             assertTrue(submitted.await(MEDIUM_DELAY_MS, MILLISECONDS));
600             t.interrupt();
601             t.join();
602         } finally {
603             quittingTime.countDown();
604             joinPool(p);
605         }
606     }
607 
608     /**
609      * get of submit(callable) throws ExecutionException if callable
610      * throws exception
611      */
testSubmitEE()612     public void testSubmitEE() throws Throwable {
613         ForkJoinPool p = new ForkJoinPool(1);
614         try {
615             p.submit(new Callable() {
616                 public Object call() { throw new ArithmeticException(); }})
617                 .get();
618             shouldThrow();
619         } catch (ExecutionException success) {
620             assertTrue(success.getCause() instanceof ArithmeticException);
621         } finally {
622             joinPool(p);
623         }
624     }
625 
626     /**
627      * invokeAny(null) throws NullPointerException
628      */
testInvokeAny1()629     public void testInvokeAny1() throws Throwable {
630         ExecutorService e = new ForkJoinPool(1);
631         try {
632             e.invokeAny(null);
633             shouldThrow();
634         } catch (NullPointerException success) {
635         } finally {
636             joinPool(e);
637         }
638     }
639 
640     /**
641      * invokeAny(empty collection) throws IllegalArgumentException
642      */
testInvokeAny2()643     public void testInvokeAny2() throws Throwable {
644         ExecutorService e = new ForkJoinPool(1);
645         try {
646             e.invokeAny(new ArrayList<Callable<String>>());
647             shouldThrow();
648         } catch (IllegalArgumentException success) {
649         } finally {
650             joinPool(e);
651         }
652     }
653 
654     /**
655      * invokeAny(c) throws NullPointerException if c has a single null element
656      */
testInvokeAny3()657     public void testInvokeAny3() throws Throwable {
658         ExecutorService e = new ForkJoinPool(1);
659         List<Callable<String>> l = new ArrayList<Callable<String>>();
660         l.add(null);
661         try {
662             e.invokeAny(l);
663             shouldThrow();
664         } catch (NullPointerException success) {
665         } finally {
666             joinPool(e);
667         }
668     }
669 
670     /**
671      * invokeAny(c) throws NullPointerException if c has null elements
672      */
testInvokeAny4()673     public void testInvokeAny4() throws Throwable {
674         CountDownLatch latch = new CountDownLatch(1);
675         ExecutorService e = new ForkJoinPool(1);
676         List<Callable<String>> l = new ArrayList<Callable<String>>();
677         l.add(latchAwaitingStringTask(latch));
678         l.add(null);
679         try {
680             e.invokeAny(l);
681             shouldThrow();
682         } catch (NullPointerException success) {
683         } finally {
684             latch.countDown();
685             joinPool(e);
686         }
687     }
688 
689     /**
690      * invokeAny(c) throws ExecutionException if no task in c completes
691      */
testInvokeAny5()692     public void testInvokeAny5() throws Throwable {
693         ExecutorService e = new ForkJoinPool(1);
694         List<Callable<String>> l = new ArrayList<Callable<String>>();
695         l.add(new NPETask());
696         try {
697             e.invokeAny(l);
698             shouldThrow();
699         } catch (ExecutionException success) {
700             assertTrue(success.getCause() instanceof NullPointerException);
701         } finally {
702             joinPool(e);
703         }
704     }
705 
706     /**
707      * invokeAny(c) returns result of some task in c if at least one completes
708      */
testInvokeAny6()709     public void testInvokeAny6() throws Throwable {
710         ExecutorService e = new ForkJoinPool(1);
711         try {
712             List<Callable<String>> l = new ArrayList<Callable<String>>();
713             l.add(new StringTask());
714             l.add(new StringTask());
715             String result = e.invokeAny(l);
716             assertSame(TEST_STRING, result);
717         } finally {
718             joinPool(e);
719         }
720     }
721 
722     /**
723      * invokeAll(null) throws NullPointerException
724      */
testInvokeAll1()725     public void testInvokeAll1() throws Throwable {
726         ExecutorService e = new ForkJoinPool(1);
727         try {
728             e.invokeAll(null);
729             shouldThrow();
730         } catch (NullPointerException success) {
731         } finally {
732             joinPool(e);
733         }
734     }
735 
736     /**
737      * invokeAll(empty collection) returns empty collection
738      */
testInvokeAll2()739     public void testInvokeAll2() throws InterruptedException {
740         ExecutorService e = new ForkJoinPool(1);
741         try {
742             List<Future<String>> r
743                 = e.invokeAll(new ArrayList<Callable<String>>());
744             assertTrue(r.isEmpty());
745         } finally {
746             joinPool(e);
747         }
748     }
749 
750     /**
751      * invokeAll(c) throws NullPointerException if c has null elements
752      */
testInvokeAll3()753     public void testInvokeAll3() throws InterruptedException {
754         ExecutorService e = new ForkJoinPool(1);
755         List<Callable<String>> l = new ArrayList<Callable<String>>();
756         l.add(new StringTask());
757         l.add(null);
758         try {
759             e.invokeAll(l);
760             shouldThrow();
761         } catch (NullPointerException success) {
762         } finally {
763             joinPool(e);
764         }
765     }
766 
767     /**
768      * get of returned element of invokeAll(c) throws
769      * ExecutionException on failed task
770      */
testInvokeAll4()771     public void testInvokeAll4() throws Throwable {
772         ExecutorService e = new ForkJoinPool(1);
773         List<Callable<String>> l = new ArrayList<Callable<String>>();
774         l.add(new NPETask());
775         List<Future<String>> futures = e.invokeAll(l);
776         assertEquals(1, futures.size());
777         try {
778             futures.get(0).get();
779             shouldThrow();
780         } catch (ExecutionException success) {
781             assertTrue(success.getCause() instanceof NullPointerException);
782         } finally {
783             joinPool(e);
784         }
785     }
786 
787     /**
788      * invokeAll(c) returns results of all completed tasks in c
789      */
testInvokeAll5()790     public void testInvokeAll5() throws Throwable {
791         ExecutorService e = new ForkJoinPool(1);
792         try {
793             List<Callable<String>> l = new ArrayList<Callable<String>>();
794             l.add(new StringTask());
795             l.add(new StringTask());
796             List<Future<String>> futures = e.invokeAll(l);
797             assertEquals(2, futures.size());
798             for (Future<String> future : futures)
799                 assertSame(TEST_STRING, future.get());
800         } finally {
801             joinPool(e);
802         }
803     }
804 
805     /**
806      * timed invokeAny(null) throws NullPointerException
807      */
testTimedInvokeAny1()808     public void testTimedInvokeAny1() throws Throwable {
809         ExecutorService e = new ForkJoinPool(1);
810         try {
811             e.invokeAny(null, MEDIUM_DELAY_MS, MILLISECONDS);
812             shouldThrow();
813         } catch (NullPointerException success) {
814         } finally {
815             joinPool(e);
816         }
817     }
818 
819     /**
820      * timed invokeAny(null time unit) throws NullPointerException
821      */
testTimedInvokeAnyNullTimeUnit()822     public void testTimedInvokeAnyNullTimeUnit() throws Throwable {
823         ExecutorService e = new ForkJoinPool(1);
824         List<Callable<String>> l = new ArrayList<Callable<String>>();
825         l.add(new StringTask());
826         try {
827             e.invokeAny(l, MEDIUM_DELAY_MS, null);
828             shouldThrow();
829         } catch (NullPointerException success) {
830         } finally {
831             joinPool(e);
832         }
833     }
834 
835     /**
836      * timed invokeAny(empty collection) throws IllegalArgumentException
837      */
testTimedInvokeAny2()838     public void testTimedInvokeAny2() throws Throwable {
839         ExecutorService e = new ForkJoinPool(1);
840         try {
841             e.invokeAny(new ArrayList<Callable<String>>(),
842                         MEDIUM_DELAY_MS, MILLISECONDS);
843             shouldThrow();
844         } catch (IllegalArgumentException success) {
845         } finally {
846             joinPool(e);
847         }
848     }
849 
850     /**
851      * timed invokeAny(c) throws NullPointerException if c has null elements
852      */
testTimedInvokeAny3()853     public void testTimedInvokeAny3() throws Throwable {
854         CountDownLatch latch = new CountDownLatch(1);
855         ExecutorService e = new ForkJoinPool(1);
856         List<Callable<String>> l = new ArrayList<Callable<String>>();
857         l.add(latchAwaitingStringTask(latch));
858         l.add(null);
859         try {
860             e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
861             shouldThrow();
862         } catch (NullPointerException success) {
863         } finally {
864             latch.countDown();
865             joinPool(e);
866         }
867     }
868 
869     /**
870      * timed invokeAny(c) throws ExecutionException if no task completes
871      */
testTimedInvokeAny4()872     public void testTimedInvokeAny4() throws Throwable {
873         ExecutorService e = new ForkJoinPool(1);
874         List<Callable<String>> l = new ArrayList<Callable<String>>();
875         l.add(new NPETask());
876         try {
877             e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
878             shouldThrow();
879         } catch (ExecutionException success) {
880             assertTrue(success.getCause() instanceof NullPointerException);
881         } finally {
882             joinPool(e);
883         }
884     }
885 
886     /**
887      * timed invokeAny(c) returns result of some task in c
888      */
testTimedInvokeAny5()889     public void testTimedInvokeAny5() throws Throwable {
890         ExecutorService e = new ForkJoinPool(1);
891         try {
892             List<Callable<String>> l = new ArrayList<Callable<String>>();
893             l.add(new StringTask());
894             l.add(new StringTask());
895             String result = e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
896             assertSame(TEST_STRING, result);
897         } finally {
898             joinPool(e);
899         }
900     }
901 
902     /**
903      * timed invokeAll(null) throws NullPointerException
904      */
testTimedInvokeAll1()905     public void testTimedInvokeAll1() throws Throwable {
906         ExecutorService e = new ForkJoinPool(1);
907         try {
908             e.invokeAll(null, MEDIUM_DELAY_MS, MILLISECONDS);
909             shouldThrow();
910         } catch (NullPointerException success) {
911         } finally {
912             joinPool(e);
913         }
914     }
915 
916     /**
917      * timed invokeAll(null time unit) throws NullPointerException
918      */
testTimedInvokeAllNullTimeUnit()919     public void testTimedInvokeAllNullTimeUnit() throws Throwable {
920         ExecutorService e = new ForkJoinPool(1);
921         List<Callable<String>> l = new ArrayList<Callable<String>>();
922         l.add(new StringTask());
923         try {
924             e.invokeAll(l, MEDIUM_DELAY_MS, null);
925             shouldThrow();
926         } catch (NullPointerException success) {
927         } finally {
928             joinPool(e);
929         }
930     }
931 
932     /**
933      * timed invokeAll(empty collection) returns empty collection
934      */
testTimedInvokeAll2()935     public void testTimedInvokeAll2() throws InterruptedException {
936         ExecutorService e = new ForkJoinPool(1);
937         try {
938             List<Future<String>> r
939                 = e.invokeAll(new ArrayList<Callable<String>>(),
940                               MEDIUM_DELAY_MS, MILLISECONDS);
941             assertTrue(r.isEmpty());
942         } finally {
943             joinPool(e);
944         }
945     }
946 
947     /**
948      * timed invokeAll(c) throws NullPointerException if c has null elements
949      */
testTimedInvokeAll3()950     public void testTimedInvokeAll3() throws InterruptedException {
951         ExecutorService e = new ForkJoinPool(1);
952         List<Callable<String>> l = new ArrayList<Callable<String>>();
953         l.add(new StringTask());
954         l.add(null);
955         try {
956             e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
957             shouldThrow();
958         } catch (NullPointerException success) {
959         } finally {
960             joinPool(e);
961         }
962     }
963 
964     /**
965      * get of returned element of invokeAll(c) throws exception on failed task
966      */
testTimedInvokeAll4()967     public void testTimedInvokeAll4() throws Throwable {
968         ExecutorService e = new ForkJoinPool(1);
969         List<Callable<String>> l = new ArrayList<Callable<String>>();
970         l.add(new NPETask());
971         List<Future<String>> futures
972             = e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
973         assertEquals(1, futures.size());
974         try {
975             futures.get(0).get();
976             shouldThrow();
977         } catch (ExecutionException success) {
978             assertTrue(success.getCause() instanceof NullPointerException);
979         } finally {
980             joinPool(e);
981         }
982     }
983 
984     /**
985      * timed invokeAll(c) returns results of all completed tasks in c
986      */
testTimedInvokeAll5()987     public void testTimedInvokeAll5() throws Throwable {
988         ExecutorService e = new ForkJoinPool(1);
989         try {
990             List<Callable<String>> l = new ArrayList<Callable<String>>();
991             l.add(new StringTask());
992             l.add(new StringTask());
993             List<Future<String>> futures
994                 = e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
995             assertEquals(2, futures.size());
996             for (Future<String> future : futures)
997                 assertSame(TEST_STRING, future.get());
998         } finally {
999             joinPool(e);
1000         }
1001     }
1002 
1003 }
1004