ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/test/tck/ThreadPoolExecutorSubclassTest.java
Revision: 1.33
Committed: Wed Dec 31 19:05:43 2014 UTC (9 years, 4 months ago) by jsr166
Branch: MAIN
Changes since 1.32: +24 -3 lines
Log Message:
no wildcard imports

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/publicdomain/zero/1.0/
5 * Other contributors include Andrew Wright, Jeffrey Hayes,
6 * Pat Fisher, Mike Judd.
7 */
8
9 import static java.util.concurrent.TimeUnit.MILLISECONDS;
10
11 import java.util.ArrayList;
12 import java.util.List;
13 import java.util.concurrent.ArrayBlockingQueue;
14 import java.util.concurrent.BlockingQueue;
15 import java.util.concurrent.Callable;
16 import java.util.concurrent.CountDownLatch;
17 import java.util.concurrent.ExecutionException;
18 import java.util.concurrent.Executors;
19 import java.util.concurrent.ExecutorService;
20 import java.util.concurrent.Future;
21 import java.util.concurrent.FutureTask;
22 import java.util.concurrent.LinkedBlockingQueue;
23 import java.util.concurrent.RejectedExecutionException;
24 import java.util.concurrent.RejectedExecutionHandler;
25 import java.util.concurrent.RunnableFuture;
26 import java.util.concurrent.SynchronousQueue;
27 import java.util.concurrent.ThreadFactory;
28 import java.util.concurrent.ThreadPoolExecutor;
29 import java.util.concurrent.TimeoutException;
30 import java.util.concurrent.TimeUnit;
31 import java.util.concurrent.locks.Condition;
32 import java.util.concurrent.locks.ReentrantLock;
33
34 import junit.framework.Test;
35 import junit.framework.TestSuite;
36
37 public class ThreadPoolExecutorSubclassTest extends JSR166TestCase {
38 public static void main(String[] args) {
39 junit.textui.TestRunner.run(suite());
40 }
41 public static Test suite() {
42 return new TestSuite(ThreadPoolExecutorSubclassTest.class);
43 }
44
45 static class CustomTask<V> implements RunnableFuture<V> {
46 final Callable<V> callable;
47 final ReentrantLock lock = new ReentrantLock();
48 final Condition cond = lock.newCondition();
49 boolean done;
50 boolean cancelled;
51 V result;
52 Thread thread;
53 Exception exception;
54 CustomTask(Callable<V> c) {
55 if (c == null) throw new NullPointerException();
56 callable = c;
57 }
58 CustomTask(final Runnable r, final V res) {
59 if (r == null) throw new NullPointerException();
60 callable = new Callable<V>() {
61 public V call() throws Exception { r.run(); return res; }};
62 }
63 public boolean isDone() {
64 lock.lock(); try { return done; } finally { lock.unlock() ; }
65 }
66 public boolean isCancelled() {
67 lock.lock(); try { return cancelled; } finally { lock.unlock() ; }
68 }
69 public boolean cancel(boolean mayInterrupt) {
70 lock.lock();
71 try {
72 if (!done) {
73 cancelled = true;
74 done = true;
75 if (mayInterrupt && thread != null)
76 thread.interrupt();
77 return true;
78 }
79 return false;
80 }
81 finally { lock.unlock() ; }
82 }
83 public void run() {
84 lock.lock();
85 try {
86 if (done)
87 return;
88 thread = Thread.currentThread();
89 }
90 finally { lock.unlock() ; }
91 V v = null;
92 Exception e = null;
93 try {
94 v = callable.call();
95 }
96 catch (Exception ex) {
97 e = ex;
98 }
99 lock.lock();
100 try {
101 result = v;
102 exception = e;
103 done = true;
104 thread = null;
105 cond.signalAll();
106 }
107 finally { lock.unlock(); }
108 }
109 public V get() throws InterruptedException, ExecutionException {
110 lock.lock();
111 try {
112 while (!done)
113 cond.await();
114 if (exception != null)
115 throw new ExecutionException(exception);
116 return result;
117 }
118 finally { lock.unlock(); }
119 }
120 public V get(long timeout, TimeUnit unit)
121 throws InterruptedException, ExecutionException, TimeoutException {
122 long nanos = unit.toNanos(timeout);
123 lock.lock();
124 try {
125 for (;;) {
126 if (done) break;
127 if (nanos < 0)
128 throw new TimeoutException();
129 nanos = cond.awaitNanos(nanos);
130 }
131 if (exception != null)
132 throw new ExecutionException(exception);
133 return result;
134 }
135 finally { lock.unlock(); }
136 }
137 }
138
139 static class CustomTPE extends ThreadPoolExecutor {
140 protected <V> RunnableFuture<V> newTaskFor(Callable<V> c) {
141 return new CustomTask<V>(c);
142 }
143 protected <V> RunnableFuture<V> newTaskFor(Runnable r, V v) {
144 return new CustomTask<V>(r, v);
145 }
146
147 CustomTPE(int corePoolSize,
148 int maximumPoolSize,
149 long keepAliveTime,
150 TimeUnit unit,
151 BlockingQueue<Runnable> workQueue) {
152 super(corePoolSize, maximumPoolSize, keepAliveTime, unit,
153 workQueue);
154 }
155 CustomTPE(int corePoolSize,
156 int maximumPoolSize,
157 long keepAliveTime,
158 TimeUnit unit,
159 BlockingQueue<Runnable> workQueue,
160 ThreadFactory threadFactory) {
161 super(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue,
162 threadFactory);
163 }
164
165 CustomTPE(int corePoolSize,
166 int maximumPoolSize,
167 long keepAliveTime,
168 TimeUnit unit,
169 BlockingQueue<Runnable> workQueue,
170 RejectedExecutionHandler handler) {
171 super(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue,
172 handler);
173 }
174 CustomTPE(int corePoolSize,
175 int maximumPoolSize,
176 long keepAliveTime,
177 TimeUnit unit,
178 BlockingQueue<Runnable> workQueue,
179 ThreadFactory threadFactory,
180 RejectedExecutionHandler handler) {
181 super(corePoolSize, maximumPoolSize, keepAliveTime, unit,
182 workQueue, threadFactory, handler);
183 }
184
185 final CountDownLatch beforeCalled = new CountDownLatch(1);
186 final CountDownLatch afterCalled = new CountDownLatch(1);
187 final CountDownLatch terminatedCalled = new CountDownLatch(1);
188
189 public CustomTPE() {
190 super(1, 1, LONG_DELAY_MS, MILLISECONDS, new SynchronousQueue<Runnable>());
191 }
192 protected void beforeExecute(Thread t, Runnable r) {
193 beforeCalled.countDown();
194 }
195 protected void afterExecute(Runnable r, Throwable t) {
196 afterCalled.countDown();
197 }
198 protected void terminated() {
199 terminatedCalled.countDown();
200 }
201
202 public boolean beforeCalled() {
203 return beforeCalled.getCount() == 0;
204 }
205 public boolean afterCalled() {
206 return afterCalled.getCount() == 0;
207 }
208 public boolean terminatedCalled() {
209 return terminatedCalled.getCount() == 0;
210 }
211 }
212
213 static class FailingThreadFactory implements ThreadFactory {
214 int calls = 0;
215 public Thread newThread(Runnable r) {
216 if (++calls > 1) return null;
217 return new Thread(r);
218 }
219 }
220
221 /**
222 * execute successfully executes a runnable
223 */
224 public void testExecute() throws InterruptedException {
225 final ThreadPoolExecutor p =
226 new CustomTPE(1, 1,
227 LONG_DELAY_MS, MILLISECONDS,
228 new ArrayBlockingQueue<Runnable>(10));
229 final CountDownLatch done = new CountDownLatch(1);
230 final Runnable task = new CheckedRunnable() {
231 public void realRun() {
232 done.countDown();
233 }};
234 try {
235 p.execute(task);
236 assertTrue(done.await(SMALL_DELAY_MS, MILLISECONDS));
237 } finally {
238 joinPool(p);
239 }
240 }
241
242 /**
243 * getActiveCount increases but doesn't overestimate, when a
244 * thread becomes active
245 */
246 public void testGetActiveCount() throws InterruptedException {
247 final ThreadPoolExecutor p =
248 new CustomTPE(2, 2,
249 LONG_DELAY_MS, MILLISECONDS,
250 new ArrayBlockingQueue<Runnable>(10));
251 final CountDownLatch threadStarted = new CountDownLatch(1);
252 final CountDownLatch done = new CountDownLatch(1);
253 try {
254 assertEquals(0, p.getActiveCount());
255 p.execute(new CheckedRunnable() {
256 public void realRun() throws InterruptedException {
257 threadStarted.countDown();
258 assertEquals(1, p.getActiveCount());
259 done.await();
260 }});
261 assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
262 assertEquals(1, p.getActiveCount());
263 } finally {
264 done.countDown();
265 joinPool(p);
266 }
267 }
268
269 /**
270 * prestartCoreThread starts a thread if under corePoolSize, else doesn't
271 */
272 public void testPrestartCoreThread() {
273 ThreadPoolExecutor p = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
274 assertEquals(0, p.getPoolSize());
275 assertTrue(p.prestartCoreThread());
276 assertEquals(1, p.getPoolSize());
277 assertTrue(p.prestartCoreThread());
278 assertEquals(2, p.getPoolSize());
279 assertFalse(p.prestartCoreThread());
280 assertEquals(2, p.getPoolSize());
281 joinPool(p);
282 }
283
284 /**
285 * prestartAllCoreThreads starts all corePoolSize threads
286 */
287 public void testPrestartAllCoreThreads() {
288 ThreadPoolExecutor p = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
289 assertEquals(0, p.getPoolSize());
290 p.prestartAllCoreThreads();
291 assertEquals(2, p.getPoolSize());
292 p.prestartAllCoreThreads();
293 assertEquals(2, p.getPoolSize());
294 joinPool(p);
295 }
296
297 /**
298 * getCompletedTaskCount increases, but doesn't overestimate,
299 * when tasks complete
300 */
301 public void testGetCompletedTaskCount() throws InterruptedException {
302 final ThreadPoolExecutor p =
303 new CustomTPE(2, 2,
304 LONG_DELAY_MS, MILLISECONDS,
305 new ArrayBlockingQueue<Runnable>(10));
306 final CountDownLatch threadStarted = new CountDownLatch(1);
307 final CountDownLatch threadProceed = new CountDownLatch(1);
308 final CountDownLatch threadDone = new CountDownLatch(1);
309 try {
310 assertEquals(0, p.getCompletedTaskCount());
311 p.execute(new CheckedRunnable() {
312 public void realRun() throws InterruptedException {
313 threadStarted.countDown();
314 assertEquals(0, p.getCompletedTaskCount());
315 threadProceed.await();
316 threadDone.countDown();
317 }});
318 await(threadStarted);
319 assertEquals(0, p.getCompletedTaskCount());
320 threadProceed.countDown();
321 threadDone.await();
322 long startTime = System.nanoTime();
323 while (p.getCompletedTaskCount() != 1) {
324 if (millisElapsedSince(startTime) > LONG_DELAY_MS)
325 fail("timed out");
326 Thread.yield();
327 }
328 } finally {
329 joinPool(p);
330 }
331 }
332
333 /**
334 * getCorePoolSize returns size given in constructor if not otherwise set
335 */
336 public void testGetCorePoolSize() {
337 ThreadPoolExecutor p = new CustomTPE(1, 1, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
338 assertEquals(1, p.getCorePoolSize());
339 joinPool(p);
340 }
341
342 /**
343 * getKeepAliveTime returns value given in constructor if not otherwise set
344 */
345 public void testGetKeepAliveTime() {
346 ThreadPoolExecutor p = new CustomTPE(2, 2, 1000, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
347 assertEquals(1, p.getKeepAliveTime(TimeUnit.SECONDS));
348 joinPool(p);
349 }
350
351 /**
352 * getThreadFactory returns factory in constructor if not set
353 */
354 public void testGetThreadFactory() {
355 ThreadFactory tf = new SimpleThreadFactory();
356 ThreadPoolExecutor p = new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10), tf, new NoOpREHandler());
357 assertSame(tf, p.getThreadFactory());
358 joinPool(p);
359 }
360
361 /**
362 * setThreadFactory sets the thread factory returned by getThreadFactory
363 */
364 public void testSetThreadFactory() {
365 ThreadPoolExecutor p = new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
366 ThreadFactory tf = new SimpleThreadFactory();
367 p.setThreadFactory(tf);
368 assertSame(tf, p.getThreadFactory());
369 joinPool(p);
370 }
371
372 /**
373 * setThreadFactory(null) throws NPE
374 */
375 public void testSetThreadFactoryNull() {
376 ThreadPoolExecutor p = new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
377 try {
378 p.setThreadFactory(null);
379 shouldThrow();
380 } catch (NullPointerException success) {
381 } finally {
382 joinPool(p);
383 }
384 }
385
386 /**
387 * getRejectedExecutionHandler returns handler in constructor if not set
388 */
389 public void testGetRejectedExecutionHandler() {
390 RejectedExecutionHandler h = new NoOpREHandler();
391 ThreadPoolExecutor p = new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10), h);
392 assertSame(h, p.getRejectedExecutionHandler());
393 joinPool(p);
394 }
395
396 /**
397 * setRejectedExecutionHandler sets the handler returned by
398 * getRejectedExecutionHandler
399 */
400 public void testSetRejectedExecutionHandler() {
401 ThreadPoolExecutor p = new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
402 RejectedExecutionHandler h = new NoOpREHandler();
403 p.setRejectedExecutionHandler(h);
404 assertSame(h, p.getRejectedExecutionHandler());
405 joinPool(p);
406 }
407
408 /**
409 * setRejectedExecutionHandler(null) throws NPE
410 */
411 public void testSetRejectedExecutionHandlerNull() {
412 ThreadPoolExecutor p = new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
413 try {
414 p.setRejectedExecutionHandler(null);
415 shouldThrow();
416 } catch (NullPointerException success) {
417 } finally {
418 joinPool(p);
419 }
420 }
421
422 /**
423 * getLargestPoolSize increases, but doesn't overestimate, when
424 * multiple threads active
425 */
426 public void testGetLargestPoolSize() throws InterruptedException {
427 final int THREADS = 3;
428 final ThreadPoolExecutor p =
429 new CustomTPE(THREADS, THREADS,
430 LONG_DELAY_MS, MILLISECONDS,
431 new ArrayBlockingQueue<Runnable>(10));
432 final CountDownLatch threadsStarted = new CountDownLatch(THREADS);
433 final CountDownLatch done = new CountDownLatch(1);
434 try {
435 assertEquals(0, p.getLargestPoolSize());
436 for (int i = 0; i < THREADS; i++)
437 p.execute(new CheckedRunnable() {
438 public void realRun() throws InterruptedException {
439 threadsStarted.countDown();
440 done.await();
441 assertEquals(THREADS, p.getLargestPoolSize());
442 }});
443 assertTrue(threadsStarted.await(SMALL_DELAY_MS, MILLISECONDS));
444 assertEquals(THREADS, p.getLargestPoolSize());
445 } finally {
446 done.countDown();
447 joinPool(p);
448 assertEquals(THREADS, p.getLargestPoolSize());
449 }
450 }
451
452 /**
453 * getMaximumPoolSize returns value given in constructor if not
454 * otherwise set
455 */
456 public void testGetMaximumPoolSize() {
457 ThreadPoolExecutor p = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
458 assertEquals(2, p.getMaximumPoolSize());
459 joinPool(p);
460 }
461
462 /**
463 * getPoolSize increases, but doesn't overestimate, when threads
464 * become active
465 */
466 public void testGetPoolSize() throws InterruptedException {
467 final ThreadPoolExecutor p =
468 new CustomTPE(1, 1,
469 LONG_DELAY_MS, MILLISECONDS,
470 new ArrayBlockingQueue<Runnable>(10));
471 final CountDownLatch threadStarted = new CountDownLatch(1);
472 final CountDownLatch done = new CountDownLatch(1);
473 try {
474 assertEquals(0, p.getPoolSize());
475 p.execute(new CheckedRunnable() {
476 public void realRun() throws InterruptedException {
477 threadStarted.countDown();
478 assertEquals(1, p.getPoolSize());
479 done.await();
480 }});
481 assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
482 assertEquals(1, p.getPoolSize());
483 } finally {
484 done.countDown();
485 joinPool(p);
486 }
487 }
488
489 /**
490 * getTaskCount increases, but doesn't overestimate, when tasks submitted
491 */
492 public void testGetTaskCount() throws InterruptedException {
493 final ThreadPoolExecutor p =
494 new CustomTPE(1, 1,
495 LONG_DELAY_MS, MILLISECONDS,
496 new ArrayBlockingQueue<Runnable>(10));
497 final CountDownLatch threadStarted = new CountDownLatch(1);
498 final CountDownLatch done = new CountDownLatch(1);
499 try {
500 assertEquals(0, p.getTaskCount());
501 p.execute(new CheckedRunnable() {
502 public void realRun() throws InterruptedException {
503 threadStarted.countDown();
504 assertEquals(1, p.getTaskCount());
505 done.await();
506 }});
507 assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
508 assertEquals(1, p.getTaskCount());
509 } finally {
510 done.countDown();
511 joinPool(p);
512 }
513 }
514
515 /**
516 * isShutdown is false before shutdown, true after
517 */
518 public void testIsShutdown() {
519
520 ThreadPoolExecutor p = new CustomTPE(1, 1, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
521 assertFalse(p.isShutdown());
522 try { p.shutdown(); } catch (SecurityException ok) { return; }
523 assertTrue(p.isShutdown());
524 joinPool(p);
525 }
526
527 /**
528 * isTerminated is false before termination, true after
529 */
530 public void testIsTerminated() throws InterruptedException {
531 final ThreadPoolExecutor p =
532 new CustomTPE(1, 1,
533 LONG_DELAY_MS, MILLISECONDS,
534 new ArrayBlockingQueue<Runnable>(10));
535 final CountDownLatch threadStarted = new CountDownLatch(1);
536 final CountDownLatch done = new CountDownLatch(1);
537 try {
538 assertFalse(p.isTerminating());
539 p.execute(new CheckedRunnable() {
540 public void realRun() throws InterruptedException {
541 assertFalse(p.isTerminating());
542 threadStarted.countDown();
543 done.await();
544 }});
545 assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
546 assertFalse(p.isTerminating());
547 done.countDown();
548 } finally {
549 try { p.shutdown(); } catch (SecurityException ok) { return; }
550 }
551 assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
552 assertTrue(p.isTerminated());
553 assertFalse(p.isTerminating());
554 }
555
556 /**
557 * isTerminating is not true when running or when terminated
558 */
559 public void testIsTerminating() throws InterruptedException {
560 final ThreadPoolExecutor p =
561 new CustomTPE(1, 1,
562 LONG_DELAY_MS, MILLISECONDS,
563 new ArrayBlockingQueue<Runnable>(10));
564 final CountDownLatch threadStarted = new CountDownLatch(1);
565 final CountDownLatch done = new CountDownLatch(1);
566 try {
567 assertFalse(p.isTerminating());
568 p.execute(new CheckedRunnable() {
569 public void realRun() throws InterruptedException {
570 assertFalse(p.isTerminating());
571 threadStarted.countDown();
572 done.await();
573 }});
574 assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
575 assertFalse(p.isTerminating());
576 done.countDown();
577 } finally {
578 try { p.shutdown(); } catch (SecurityException ok) { return; }
579 }
580 assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
581 assertTrue(p.isTerminated());
582 assertFalse(p.isTerminating());
583 }
584
585 /**
586 * getQueue returns the work queue, which contains queued tasks
587 */
588 public void testGetQueue() throws InterruptedException {
589 final BlockingQueue<Runnable> q = new ArrayBlockingQueue<Runnable>(10);
590 final ThreadPoolExecutor p =
591 new CustomTPE(1, 1,
592 LONG_DELAY_MS, MILLISECONDS,
593 q);
594 final CountDownLatch threadStarted = new CountDownLatch(1);
595 final CountDownLatch done = new CountDownLatch(1);
596 try {
597 FutureTask[] tasks = new FutureTask[5];
598 for (int i = 0; i < tasks.length; i++) {
599 Callable task = new CheckedCallable<Boolean>() {
600 public Boolean realCall() throws InterruptedException {
601 threadStarted.countDown();
602 assertSame(q, p.getQueue());
603 done.await();
604 return Boolean.TRUE;
605 }};
606 tasks[i] = new FutureTask(task);
607 p.execute(tasks[i]);
608 }
609 assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
610 assertSame(q, p.getQueue());
611 assertFalse(q.contains(tasks[0]));
612 assertTrue(q.contains(tasks[tasks.length - 1]));
613 assertEquals(tasks.length - 1, q.size());
614 } finally {
615 done.countDown();
616 joinPool(p);
617 }
618 }
619
620 /**
621 * remove(task) removes queued task, and fails to remove active task
622 */
623 public void testRemove() throws InterruptedException {
624 BlockingQueue<Runnable> q = new ArrayBlockingQueue<Runnable>(10);
625 final ThreadPoolExecutor p =
626 new CustomTPE(1, 1,
627 LONG_DELAY_MS, MILLISECONDS,
628 q);
629 Runnable[] tasks = new Runnable[6];
630 final CountDownLatch threadStarted = new CountDownLatch(1);
631 final CountDownLatch done = new CountDownLatch(1);
632 try {
633 for (int i = 0; i < tasks.length; i++) {
634 tasks[i] = new CheckedRunnable() {
635 public void realRun() throws InterruptedException {
636 threadStarted.countDown();
637 done.await();
638 }};
639 p.execute(tasks[i]);
640 }
641 assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
642 assertFalse(p.remove(tasks[0]));
643 assertTrue(q.contains(tasks[4]));
644 assertTrue(q.contains(tasks[3]));
645 assertTrue(p.remove(tasks[4]));
646 assertFalse(p.remove(tasks[4]));
647 assertFalse(q.contains(tasks[4]));
648 assertTrue(q.contains(tasks[3]));
649 assertTrue(p.remove(tasks[3]));
650 assertFalse(q.contains(tasks[3]));
651 } finally {
652 done.countDown();
653 joinPool(p);
654 }
655 }
656
657 /**
658 * purge removes cancelled tasks from the queue
659 */
660 public void testPurge() throws InterruptedException {
661 final CountDownLatch threadStarted = new CountDownLatch(1);
662 final CountDownLatch done = new CountDownLatch(1);
663 final BlockingQueue<Runnable> q = new ArrayBlockingQueue<Runnable>(10);
664 final ThreadPoolExecutor p =
665 new CustomTPE(1, 1,
666 LONG_DELAY_MS, MILLISECONDS,
667 q);
668 FutureTask[] tasks = new FutureTask[5];
669 try {
670 for (int i = 0; i < tasks.length; i++) {
671 Callable task = new CheckedCallable<Boolean>() {
672 public Boolean realCall() throws InterruptedException {
673 threadStarted.countDown();
674 done.await();
675 return Boolean.TRUE;
676 }};
677 tasks[i] = new FutureTask(task);
678 p.execute(tasks[i]);
679 }
680 assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
681 assertEquals(tasks.length, p.getTaskCount());
682 assertEquals(tasks.length - 1, q.size());
683 assertEquals(1L, p.getActiveCount());
684 assertEquals(0L, p.getCompletedTaskCount());
685 tasks[4].cancel(true);
686 tasks[3].cancel(false);
687 p.purge();
688 assertEquals(tasks.length - 3, q.size());
689 assertEquals(tasks.length - 2, p.getTaskCount());
690 p.purge(); // Nothing to do
691 assertEquals(tasks.length - 3, q.size());
692 assertEquals(tasks.length - 2, p.getTaskCount());
693 } finally {
694 done.countDown();
695 joinPool(p);
696 }
697 }
698
699 /**
700 * shutdownNow returns a list containing tasks that were not run
701 */
702 public void testShutdownNow() {
703 ThreadPoolExecutor p = new CustomTPE(1, 1, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
704 List l;
705 try {
706 for (int i = 0; i < 5; i++)
707 p.execute(new MediumPossiblyInterruptedRunnable());
708 }
709 finally {
710 try {
711 l = p.shutdownNow();
712 } catch (SecurityException ok) { return; }
713 }
714 assertTrue(p.isShutdown());
715 assertTrue(l.size() <= 4);
716 }
717
718 // Exception Tests
719
720 /**
721 * Constructor throws if corePoolSize argument is less than zero
722 */
723 public void testConstructor1() {
724 try {
725 new CustomTPE(-1,1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
726 shouldThrow();
727 } catch (IllegalArgumentException success) {}
728 }
729
730 /**
731 * Constructor throws if maximumPoolSize is less than zero
732 */
733 public void testConstructor2() {
734 try {
735 new CustomTPE(1,-1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
736 shouldThrow();
737 } catch (IllegalArgumentException success) {}
738 }
739
740 /**
741 * Constructor throws if maximumPoolSize is equal to zero
742 */
743 public void testConstructor3() {
744 try {
745 new CustomTPE(1,0,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
746 shouldThrow();
747 } catch (IllegalArgumentException success) {}
748 }
749
750 /**
751 * Constructor throws if keepAliveTime is less than zero
752 */
753 public void testConstructor4() {
754 try {
755 new CustomTPE(1,2,-1L,MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
756 shouldThrow();
757 } catch (IllegalArgumentException success) {}
758 }
759
760 /**
761 * Constructor throws if corePoolSize is greater than the maximumPoolSize
762 */
763 public void testConstructor5() {
764 try {
765 new CustomTPE(2,1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
766 shouldThrow();
767 } catch (IllegalArgumentException success) {}
768 }
769
770 /**
771 * Constructor throws if workQueue is set to null
772 */
773 public void testConstructorNullPointerException() {
774 try {
775 new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS,null);
776 shouldThrow();
777 } catch (NullPointerException success) {}
778 }
779
780 /**
781 * Constructor throws if corePoolSize argument is less than zero
782 */
783 public void testConstructor6() {
784 try {
785 new CustomTPE(-1,1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory());
786 shouldThrow();
787 } catch (IllegalArgumentException success) {}
788 }
789
790 /**
791 * Constructor throws if maximumPoolSize is less than zero
792 */
793 public void testConstructor7() {
794 try {
795 new CustomTPE(1,-1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory());
796 shouldThrow();
797 } catch (IllegalArgumentException success) {}
798 }
799
800 /**
801 * Constructor throws if maximumPoolSize is equal to zero
802 */
803 public void testConstructor8() {
804 try {
805 new CustomTPE(1,0,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory());
806 shouldThrow();
807 } catch (IllegalArgumentException success) {}
808 }
809
810 /**
811 * Constructor throws if keepAliveTime is less than zero
812 */
813 public void testConstructor9() {
814 try {
815 new CustomTPE(1,2,-1L,MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory());
816 shouldThrow();
817 } catch (IllegalArgumentException success) {}
818 }
819
820 /**
821 * Constructor throws if corePoolSize is greater than the maximumPoolSize
822 */
823 public void testConstructor10() {
824 try {
825 new CustomTPE(2,1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory());
826 shouldThrow();
827 } catch (IllegalArgumentException success) {}
828 }
829
830 /**
831 * Constructor throws if workQueue is set to null
832 */
833 public void testConstructorNullPointerException2() {
834 try {
835 new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS,null,new SimpleThreadFactory());
836 shouldThrow();
837 } catch (NullPointerException success) {}
838 }
839
840 /**
841 * Constructor throws if threadFactory is set to null
842 */
843 public void testConstructorNullPointerException3() {
844 try {
845 ThreadFactory f = null;
846 new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS,new ArrayBlockingQueue<Runnable>(10),f);
847 shouldThrow();
848 } catch (NullPointerException success) {}
849 }
850
851 /**
852 * Constructor throws if corePoolSize argument is less than zero
853 */
854 public void testConstructor11() {
855 try {
856 new CustomTPE(-1,1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new NoOpREHandler());
857 shouldThrow();
858 } catch (IllegalArgumentException success) {}
859 }
860
861 /**
862 * Constructor throws if maximumPoolSize is less than zero
863 */
864 public void testConstructor12() {
865 try {
866 new CustomTPE(1,-1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new NoOpREHandler());
867 shouldThrow();
868 } catch (IllegalArgumentException success) {}
869 }
870
871 /**
872 * Constructor throws if maximumPoolSize is equal to zero
873 */
874 public void testConstructor13() {
875 try {
876 new CustomTPE(1,0,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new NoOpREHandler());
877 shouldThrow();
878 } catch (IllegalArgumentException success) {}
879 }
880
881 /**
882 * Constructor throws if keepAliveTime is less than zero
883 */
884 public void testConstructor14() {
885 try {
886 new CustomTPE(1,2,-1L,MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new NoOpREHandler());
887 shouldThrow();
888 } catch (IllegalArgumentException success) {}
889 }
890
891 /**
892 * Constructor throws if corePoolSize is greater than the maximumPoolSize
893 */
894 public void testConstructor15() {
895 try {
896 new CustomTPE(2,1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new NoOpREHandler());
897 shouldThrow();
898 } catch (IllegalArgumentException success) {}
899 }
900
901 /**
902 * Constructor throws if workQueue is set to null
903 */
904 public void testConstructorNullPointerException4() {
905 try {
906 new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS,null,new NoOpREHandler());
907 shouldThrow();
908 } catch (NullPointerException success) {}
909 }
910
911 /**
912 * Constructor throws if handler is set to null
913 */
914 public void testConstructorNullPointerException5() {
915 try {
916 RejectedExecutionHandler r = null;
917 new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS,new ArrayBlockingQueue<Runnable>(10),r);
918 shouldThrow();
919 } catch (NullPointerException success) {}
920 }
921
922 /**
923 * Constructor throws if corePoolSize argument is less than zero
924 */
925 public void testConstructor16() {
926 try {
927 new CustomTPE(-1,1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory(),new NoOpREHandler());
928 shouldThrow();
929 } catch (IllegalArgumentException success) {}
930 }
931
932 /**
933 * Constructor throws if maximumPoolSize is less than zero
934 */
935 public void testConstructor17() {
936 try {
937 new CustomTPE(1,-1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory(),new NoOpREHandler());
938 shouldThrow();
939 } catch (IllegalArgumentException success) {}
940 }
941
942 /**
943 * Constructor throws if maximumPoolSize is equal to zero
944 */
945 public void testConstructor18() {
946 try {
947 new CustomTPE(1,0,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory(),new NoOpREHandler());
948 shouldThrow();
949 } catch (IllegalArgumentException success) {}
950 }
951
952 /**
953 * Constructor throws if keepAliveTime is less than zero
954 */
955 public void testConstructor19() {
956 try {
957 new CustomTPE(1,2,-1L,MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory(),new NoOpREHandler());
958 shouldThrow();
959 } catch (IllegalArgumentException success) {}
960 }
961
962 /**
963 * Constructor throws if corePoolSize is greater than the maximumPoolSize
964 */
965 public void testConstructor20() {
966 try {
967 new CustomTPE(2,1,LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory(),new NoOpREHandler());
968 shouldThrow();
969 } catch (IllegalArgumentException success) {}
970 }
971
972 /**
973 * Constructor throws if workQueue is null
974 */
975 public void testConstructorNullPointerException6() {
976 try {
977 new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS,null,new SimpleThreadFactory(),new NoOpREHandler());
978 shouldThrow();
979 } catch (NullPointerException success) {}
980 }
981
982 /**
983 * Constructor throws if handler is null
984 */
985 public void testConstructorNullPointerException7() {
986 try {
987 RejectedExecutionHandler r = null;
988 new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS,new ArrayBlockingQueue<Runnable>(10),new SimpleThreadFactory(),r);
989 shouldThrow();
990 } catch (NullPointerException success) {}
991 }
992
993 /**
994 * Constructor throws if ThreadFactory is null
995 */
996 public void testConstructorNullPointerException8() {
997 try {
998 new CustomTPE(1, 2,
999 LONG_DELAY_MS, MILLISECONDS,
1000 new ArrayBlockingQueue<Runnable>(10),
1001 (ThreadFactory) null,
1002 new NoOpREHandler());
1003 shouldThrow();
1004 } catch (NullPointerException success) {}
1005 }
1006
1007 /**
1008 * execute throws RejectedExecutionException if saturated.
1009 */
1010 public void testSaturatedExecute() {
1011 ThreadPoolExecutor p =
1012 new CustomTPE(1, 1,
1013 LONG_DELAY_MS, MILLISECONDS,
1014 new ArrayBlockingQueue<Runnable>(1));
1015 final CountDownLatch done = new CountDownLatch(1);
1016 try {
1017 Runnable task = new CheckedRunnable() {
1018 public void realRun() throws InterruptedException {
1019 done.await();
1020 }};
1021 for (int i = 0; i < 2; ++i)
1022 p.execute(task);
1023 for (int i = 0; i < 2; ++i) {
1024 try {
1025 p.execute(task);
1026 shouldThrow();
1027 } catch (RejectedExecutionException success) {}
1028 assertTrue(p.getTaskCount() <= 2);
1029 }
1030 } finally {
1031 done.countDown();
1032 joinPool(p);
1033 }
1034 }
1035
1036 /**
1037 * executor using CallerRunsPolicy runs task if saturated.
1038 */
1039 public void testSaturatedExecute2() {
1040 RejectedExecutionHandler h = new CustomTPE.CallerRunsPolicy();
1041 ThreadPoolExecutor p = new CustomTPE(1, 1,
1042 LONG_DELAY_MS, MILLISECONDS,
1043 new ArrayBlockingQueue<Runnable>(1),
1044 h);
1045 try {
1046 TrackedNoOpRunnable[] tasks = new TrackedNoOpRunnable[5];
1047 for (int i = 0; i < tasks.length; ++i)
1048 tasks[i] = new TrackedNoOpRunnable();
1049 TrackedLongRunnable mr = new TrackedLongRunnable();
1050 p.execute(mr);
1051 for (int i = 0; i < tasks.length; ++i)
1052 p.execute(tasks[i]);
1053 for (int i = 1; i < tasks.length; ++i)
1054 assertTrue(tasks[i].done);
1055 try { p.shutdownNow(); } catch (SecurityException ok) { return; }
1056 } finally {
1057 joinPool(p);
1058 }
1059 }
1060
1061 /**
1062 * executor using DiscardPolicy drops task if saturated.
1063 */
1064 public void testSaturatedExecute3() {
1065 RejectedExecutionHandler h = new CustomTPE.DiscardPolicy();
1066 ThreadPoolExecutor p =
1067 new CustomTPE(1, 1,
1068 LONG_DELAY_MS, MILLISECONDS,
1069 new ArrayBlockingQueue<Runnable>(1),
1070 h);
1071 try {
1072 TrackedNoOpRunnable[] tasks = new TrackedNoOpRunnable[5];
1073 for (int i = 0; i < tasks.length; ++i)
1074 tasks[i] = new TrackedNoOpRunnable();
1075 p.execute(new TrackedLongRunnable());
1076 for (TrackedNoOpRunnable task : tasks)
1077 p.execute(task);
1078 for (TrackedNoOpRunnable task : tasks)
1079 assertFalse(task.done);
1080 try { p.shutdownNow(); } catch (SecurityException ok) { return; }
1081 } finally {
1082 joinPool(p);
1083 }
1084 }
1085
1086 /**
1087 * executor using DiscardOldestPolicy drops oldest task if saturated.
1088 */
1089 public void testSaturatedExecute4() {
1090 RejectedExecutionHandler h = new CustomTPE.DiscardOldestPolicy();
1091 ThreadPoolExecutor p = new CustomTPE(1,1, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(1), h);
1092 try {
1093 p.execute(new TrackedLongRunnable());
1094 TrackedLongRunnable r2 = new TrackedLongRunnable();
1095 p.execute(r2);
1096 assertTrue(p.getQueue().contains(r2));
1097 TrackedNoOpRunnable r3 = new TrackedNoOpRunnable();
1098 p.execute(r3);
1099 assertFalse(p.getQueue().contains(r2));
1100 assertTrue(p.getQueue().contains(r3));
1101 try { p.shutdownNow(); } catch (SecurityException ok) { return; }
1102 } finally {
1103 joinPool(p);
1104 }
1105 }
1106
1107 /**
1108 * execute throws RejectedExecutionException if shutdown
1109 */
1110 public void testRejectedExecutionExceptionOnShutdown() {
1111 ThreadPoolExecutor p =
1112 new CustomTPE(1,1,LONG_DELAY_MS, MILLISECONDS,new ArrayBlockingQueue<Runnable>(1));
1113 try { p.shutdown(); } catch (SecurityException ok) { return; }
1114 try {
1115 p.execute(new NoOpRunnable());
1116 shouldThrow();
1117 } catch (RejectedExecutionException success) {}
1118
1119 joinPool(p);
1120 }
1121
1122 /**
1123 * execute using CallerRunsPolicy drops task on shutdown
1124 */
1125 public void testCallerRunsOnShutdown() {
1126 RejectedExecutionHandler h = new CustomTPE.CallerRunsPolicy();
1127 ThreadPoolExecutor p = new CustomTPE(1,1, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(1), h);
1128
1129 try { p.shutdown(); } catch (SecurityException ok) { return; }
1130 try {
1131 TrackedNoOpRunnable r = new TrackedNoOpRunnable();
1132 p.execute(r);
1133 assertFalse(r.done);
1134 } finally {
1135 joinPool(p);
1136 }
1137 }
1138
1139 /**
1140 * execute using DiscardPolicy drops task on shutdown
1141 */
1142 public void testDiscardOnShutdown() {
1143 RejectedExecutionHandler h = new CustomTPE.DiscardPolicy();
1144 ThreadPoolExecutor p = new CustomTPE(1,1, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(1), h);
1145
1146 try { p.shutdown(); } catch (SecurityException ok) { return; }
1147 try {
1148 TrackedNoOpRunnable r = new TrackedNoOpRunnable();
1149 p.execute(r);
1150 assertFalse(r.done);
1151 } finally {
1152 joinPool(p);
1153 }
1154 }
1155
1156 /**
1157 * execute using DiscardOldestPolicy drops task on shutdown
1158 */
1159 public void testDiscardOldestOnShutdown() {
1160 RejectedExecutionHandler h = new CustomTPE.DiscardOldestPolicy();
1161 ThreadPoolExecutor p = new CustomTPE(1,1, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(1), h);
1162
1163 try { p.shutdown(); } catch (SecurityException ok) { return; }
1164 try {
1165 TrackedNoOpRunnable r = new TrackedNoOpRunnable();
1166 p.execute(r);
1167 assertFalse(r.done);
1168 } finally {
1169 joinPool(p);
1170 }
1171 }
1172
1173 /**
1174 * execute(null) throws NPE
1175 */
1176 public void testExecuteNull() {
1177 ThreadPoolExecutor p = null;
1178 try {
1179 p = new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS,new ArrayBlockingQueue<Runnable>(10));
1180 p.execute(null);
1181 shouldThrow();
1182 } catch (NullPointerException success) {}
1183
1184 joinPool(p);
1185 }
1186
1187 /**
1188 * setCorePoolSize of negative value throws IllegalArgumentException
1189 */
1190 public void testCorePoolSizeIllegalArgumentException() {
1191 ThreadPoolExecutor p =
1192 new CustomTPE(1,2,LONG_DELAY_MS, MILLISECONDS,new ArrayBlockingQueue<Runnable>(10));
1193 try {
1194 p.setCorePoolSize(-1);
1195 shouldThrow();
1196 } catch (IllegalArgumentException success) {
1197 } finally {
1198 try { p.shutdown(); } catch (SecurityException ok) { return; }
1199 }
1200 joinPool(p);
1201 }
1202
1203 /**
1204 * setMaximumPoolSize(int) throws IllegalArgumentException
1205 * if given a value less the core pool size
1206 */
1207 public void testMaximumPoolSizeIllegalArgumentException() {
1208 ThreadPoolExecutor p =
1209 new CustomTPE(2,3,LONG_DELAY_MS, MILLISECONDS,new ArrayBlockingQueue<Runnable>(10));
1210 try {
1211 p.setMaximumPoolSize(1);
1212 shouldThrow();
1213 } catch (IllegalArgumentException success) {
1214 } finally {
1215 try { p.shutdown(); } catch (SecurityException ok) { return; }
1216 }
1217 joinPool(p);
1218 }
1219
1220 /**
1221 * setMaximumPoolSize throws IllegalArgumentException
1222 * if given a negative value
1223 */
1224 public void testMaximumPoolSizeIllegalArgumentException2() {
1225 ThreadPoolExecutor p =
1226 new CustomTPE(2,3,LONG_DELAY_MS, MILLISECONDS,new ArrayBlockingQueue<Runnable>(10));
1227 try {
1228 p.setMaximumPoolSize(-1);
1229 shouldThrow();
1230 } catch (IllegalArgumentException success) {
1231 } finally {
1232 try { p.shutdown(); } catch (SecurityException ok) { return; }
1233 }
1234 joinPool(p);
1235 }
1236
1237 /**
1238 * setKeepAliveTime throws IllegalArgumentException
1239 * when given a negative value
1240 */
1241 public void testKeepAliveTimeIllegalArgumentException() {
1242 ThreadPoolExecutor p =
1243 new CustomTPE(2,3,LONG_DELAY_MS, MILLISECONDS,new ArrayBlockingQueue<Runnable>(10));
1244
1245 try {
1246 p.setKeepAliveTime(-1,MILLISECONDS);
1247 shouldThrow();
1248 } catch (IllegalArgumentException success) {
1249 } finally {
1250 try { p.shutdown(); } catch (SecurityException ok) { return; }
1251 }
1252 joinPool(p);
1253 }
1254
1255 /**
1256 * terminated() is called on termination
1257 */
1258 public void testTerminated() {
1259 CustomTPE p = new CustomTPE();
1260 try { p.shutdown(); } catch (SecurityException ok) { return; }
1261 assertTrue(p.terminatedCalled());
1262 joinPool(p);
1263 }
1264
1265 /**
1266 * beforeExecute and afterExecute are called when executing task
1267 */
1268 public void testBeforeAfter() throws InterruptedException {
1269 CustomTPE p = new CustomTPE();
1270 try {
1271 final CountDownLatch done = new CountDownLatch(1);
1272 p.execute(new CheckedRunnable() {
1273 public void realRun() {
1274 done.countDown();
1275 }});
1276 await(p.afterCalled);
1277 assertEquals(0, done.getCount());
1278 assertTrue(p.afterCalled());
1279 assertTrue(p.beforeCalled());
1280 try { p.shutdown(); } catch (SecurityException ok) { return; }
1281 } finally {
1282 joinPool(p);
1283 }
1284 }
1285
1286 /**
1287 * completed submit of callable returns result
1288 */
1289 public void testSubmitCallable() throws Exception {
1290 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1291 try {
1292 Future<String> future = e.submit(new StringTask());
1293 String result = future.get();
1294 assertSame(TEST_STRING, result);
1295 } finally {
1296 joinPool(e);
1297 }
1298 }
1299
1300 /**
1301 * completed submit of runnable returns successfully
1302 */
1303 public void testSubmitRunnable() throws Exception {
1304 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1305 try {
1306 Future<?> future = e.submit(new NoOpRunnable());
1307 future.get();
1308 assertTrue(future.isDone());
1309 } finally {
1310 joinPool(e);
1311 }
1312 }
1313
1314 /**
1315 * completed submit of (runnable, result) returns result
1316 */
1317 public void testSubmitRunnable2() throws Exception {
1318 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1319 try {
1320 Future<String> future = e.submit(new NoOpRunnable(), TEST_STRING);
1321 String result = future.get();
1322 assertSame(TEST_STRING, result);
1323 } finally {
1324 joinPool(e);
1325 }
1326 }
1327
1328 /**
1329 * invokeAny(null) throws NPE
1330 */
1331 public void testInvokeAny1() throws Exception {
1332 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1333 try {
1334 e.invokeAny(null);
1335 shouldThrow();
1336 } catch (NullPointerException success) {
1337 } finally {
1338 joinPool(e);
1339 }
1340 }
1341
1342 /**
1343 * invokeAny(empty collection) throws IAE
1344 */
1345 public void testInvokeAny2() throws Exception {
1346 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1347 try {
1348 e.invokeAny(new ArrayList<Callable<String>>());
1349 shouldThrow();
1350 } catch (IllegalArgumentException success) {
1351 } finally {
1352 joinPool(e);
1353 }
1354 }
1355
1356 /**
1357 * invokeAny(c) throws NPE if c has null elements
1358 */
1359 public void testInvokeAny3() throws Exception {
1360 CountDownLatch latch = new CountDownLatch(1);
1361 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1362 List<Callable<String>> l = new ArrayList<Callable<String>>();
1363 l.add(latchAwaitingStringTask(latch));
1364 l.add(null);
1365 try {
1366 e.invokeAny(l);
1367 shouldThrow();
1368 } catch (NullPointerException success) {
1369 } finally {
1370 latch.countDown();
1371 joinPool(e);
1372 }
1373 }
1374
1375 /**
1376 * invokeAny(c) throws ExecutionException if no task completes
1377 */
1378 public void testInvokeAny4() throws Exception {
1379 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1380 List<Callable<String>> l = new ArrayList<Callable<String>>();
1381 l.add(new NPETask());
1382 try {
1383 e.invokeAny(l);
1384 shouldThrow();
1385 } catch (ExecutionException success) {
1386 assertTrue(success.getCause() instanceof NullPointerException);
1387 } finally {
1388 joinPool(e);
1389 }
1390 }
1391
1392 /**
1393 * invokeAny(c) returns result of some task
1394 */
1395 public void testInvokeAny5() throws Exception {
1396 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1397 try {
1398 List<Callable<String>> l = new ArrayList<Callable<String>>();
1399 l.add(new StringTask());
1400 l.add(new StringTask());
1401 String result = e.invokeAny(l);
1402 assertSame(TEST_STRING, result);
1403 } finally {
1404 joinPool(e);
1405 }
1406 }
1407
1408 /**
1409 * invokeAll(null) throws NPE
1410 */
1411 public void testInvokeAll1() throws Exception {
1412 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1413 try {
1414 e.invokeAll(null);
1415 shouldThrow();
1416 } catch (NullPointerException success) {
1417 } finally {
1418 joinPool(e);
1419 }
1420 }
1421
1422 /**
1423 * invokeAll(empty collection) returns empty collection
1424 */
1425 public void testInvokeAll2() throws Exception {
1426 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1427 try {
1428 List<Future<String>> r = e.invokeAll(new ArrayList<Callable<String>>());
1429 assertTrue(r.isEmpty());
1430 } finally {
1431 joinPool(e);
1432 }
1433 }
1434
1435 /**
1436 * invokeAll(c) throws NPE if c has null elements
1437 */
1438 public void testInvokeAll3() throws Exception {
1439 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1440 List<Callable<String>> l = new ArrayList<Callable<String>>();
1441 l.add(new StringTask());
1442 l.add(null);
1443 try {
1444 e.invokeAll(l);
1445 shouldThrow();
1446 } catch (NullPointerException success) {
1447 } finally {
1448 joinPool(e);
1449 }
1450 }
1451
1452 /**
1453 * get of element of invokeAll(c) throws exception on failed task
1454 */
1455 public void testInvokeAll4() throws Exception {
1456 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1457 List<Callable<String>> l = new ArrayList<Callable<String>>();
1458 l.add(new NPETask());
1459 List<Future<String>> futures = e.invokeAll(l);
1460 assertEquals(1, futures.size());
1461 try {
1462 futures.get(0).get();
1463 shouldThrow();
1464 } catch (ExecutionException success) {
1465 assertTrue(success.getCause() instanceof NullPointerException);
1466 } finally {
1467 joinPool(e);
1468 }
1469 }
1470
1471 /**
1472 * invokeAll(c) returns results of all completed tasks
1473 */
1474 public void testInvokeAll5() throws Exception {
1475 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1476 try {
1477 List<Callable<String>> l = new ArrayList<Callable<String>>();
1478 l.add(new StringTask());
1479 l.add(new StringTask());
1480 List<Future<String>> futures = e.invokeAll(l);
1481 assertEquals(2, futures.size());
1482 for (Future<String> future : futures)
1483 assertSame(TEST_STRING, future.get());
1484 } finally {
1485 joinPool(e);
1486 }
1487 }
1488
1489 /**
1490 * timed invokeAny(null) throws NPE
1491 */
1492 public void testTimedInvokeAny1() throws Exception {
1493 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1494 try {
1495 e.invokeAny(null, MEDIUM_DELAY_MS, MILLISECONDS);
1496 shouldThrow();
1497 } catch (NullPointerException success) {
1498 } finally {
1499 joinPool(e);
1500 }
1501 }
1502
1503 /**
1504 * timed invokeAny(,,null) throws NPE
1505 */
1506 public void testTimedInvokeAnyNullTimeUnit() throws Exception {
1507 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1508 List<Callable<String>> l = new ArrayList<Callable<String>>();
1509 l.add(new StringTask());
1510 try {
1511 e.invokeAny(l, MEDIUM_DELAY_MS, null);
1512 shouldThrow();
1513 } catch (NullPointerException success) {
1514 } finally {
1515 joinPool(e);
1516 }
1517 }
1518
1519 /**
1520 * timed invokeAny(empty collection) throws IAE
1521 */
1522 public void testTimedInvokeAny2() throws Exception {
1523 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1524 try {
1525 e.invokeAny(new ArrayList<Callable<String>>(), MEDIUM_DELAY_MS, MILLISECONDS);
1526 shouldThrow();
1527 } catch (IllegalArgumentException success) {
1528 } finally {
1529 joinPool(e);
1530 }
1531 }
1532
1533 /**
1534 * timed invokeAny(c) throws NPE if c has null elements
1535 */
1536 public void testTimedInvokeAny3() throws Exception {
1537 CountDownLatch latch = new CountDownLatch(1);
1538 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1539 List<Callable<String>> l = new ArrayList<Callable<String>>();
1540 l.add(latchAwaitingStringTask(latch));
1541 l.add(null);
1542 try {
1543 e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
1544 shouldThrow();
1545 } catch (NullPointerException success) {
1546 } finally {
1547 latch.countDown();
1548 joinPool(e);
1549 }
1550 }
1551
1552 /**
1553 * timed invokeAny(c) throws ExecutionException if no task completes
1554 */
1555 public void testTimedInvokeAny4() throws Exception {
1556 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1557 List<Callable<String>> l = new ArrayList<Callable<String>>();
1558 l.add(new NPETask());
1559 try {
1560 e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
1561 shouldThrow();
1562 } catch (ExecutionException success) {
1563 assertTrue(success.getCause() instanceof NullPointerException);
1564 } finally {
1565 joinPool(e);
1566 }
1567 }
1568
1569 /**
1570 * timed invokeAny(c) returns result of some task
1571 */
1572 public void testTimedInvokeAny5() throws Exception {
1573 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1574 try {
1575 List<Callable<String>> l = new ArrayList<Callable<String>>();
1576 l.add(new StringTask());
1577 l.add(new StringTask());
1578 String result = e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
1579 assertSame(TEST_STRING, result);
1580 } finally {
1581 joinPool(e);
1582 }
1583 }
1584
1585 /**
1586 * timed invokeAll(null) throws NPE
1587 */
1588 public void testTimedInvokeAll1() throws Exception {
1589 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1590 try {
1591 e.invokeAll(null, MEDIUM_DELAY_MS, MILLISECONDS);
1592 shouldThrow();
1593 } catch (NullPointerException success) {
1594 } finally {
1595 joinPool(e);
1596 }
1597 }
1598
1599 /**
1600 * timed invokeAll(,,null) throws NPE
1601 */
1602 public void testTimedInvokeAllNullTimeUnit() throws Exception {
1603 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1604 List<Callable<String>> l = new ArrayList<Callable<String>>();
1605 l.add(new StringTask());
1606 try {
1607 e.invokeAll(l, MEDIUM_DELAY_MS, null);
1608 shouldThrow();
1609 } catch (NullPointerException success) {
1610 } finally {
1611 joinPool(e);
1612 }
1613 }
1614
1615 /**
1616 * timed invokeAll(empty collection) returns empty collection
1617 */
1618 public void testTimedInvokeAll2() throws Exception {
1619 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1620 try {
1621 List<Future<String>> r = e.invokeAll(new ArrayList<Callable<String>>(), MEDIUM_DELAY_MS, MILLISECONDS);
1622 assertTrue(r.isEmpty());
1623 } finally {
1624 joinPool(e);
1625 }
1626 }
1627
1628 /**
1629 * timed invokeAll(c) throws NPE if c has null elements
1630 */
1631 public void testTimedInvokeAll3() throws Exception {
1632 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1633 List<Callable<String>> l = new ArrayList<Callable<String>>();
1634 l.add(new StringTask());
1635 l.add(null);
1636 try {
1637 e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
1638 shouldThrow();
1639 } catch (NullPointerException success) {
1640 } finally {
1641 joinPool(e);
1642 }
1643 }
1644
1645 /**
1646 * get of element of invokeAll(c) throws exception on failed task
1647 */
1648 public void testTimedInvokeAll4() throws Exception {
1649 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1650 List<Callable<String>> l = new ArrayList<Callable<String>>();
1651 l.add(new NPETask());
1652 List<Future<String>> futures =
1653 e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
1654 assertEquals(1, futures.size());
1655 try {
1656 futures.get(0).get();
1657 shouldThrow();
1658 } catch (ExecutionException success) {
1659 assertTrue(success.getCause() instanceof NullPointerException);
1660 } finally {
1661 joinPool(e);
1662 }
1663 }
1664
1665 /**
1666 * timed invokeAll(c) returns results of all completed tasks
1667 */
1668 public void testTimedInvokeAll5() throws Exception {
1669 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1670 try {
1671 List<Callable<String>> l = new ArrayList<Callable<String>>();
1672 l.add(new StringTask());
1673 l.add(new StringTask());
1674 List<Future<String>> futures =
1675 e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
1676 assertEquals(2, futures.size());
1677 for (Future<String> future : futures)
1678 assertSame(TEST_STRING, future.get());
1679 } finally {
1680 joinPool(e);
1681 }
1682 }
1683
1684 /**
1685 * timed invokeAll(c) cancels tasks not completed by timeout
1686 */
1687 public void testTimedInvokeAll6() throws Exception {
1688 ExecutorService e = new CustomTPE(2, 2, LONG_DELAY_MS, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1689 try {
1690 List<Callable<String>> l = new ArrayList<Callable<String>>();
1691 l.add(new StringTask());
1692 l.add(Executors.callable(new MediumPossiblyInterruptedRunnable(), TEST_STRING));
1693 l.add(new StringTask());
1694 List<Future<String>> futures =
1695 e.invokeAll(l, SHORT_DELAY_MS, MILLISECONDS);
1696 assertEquals(l.size(), futures.size());
1697 for (Future future : futures)
1698 assertTrue(future.isDone());
1699 assertFalse(futures.get(0).isCancelled());
1700 assertTrue(futures.get(1).isCancelled());
1701 } finally {
1702 joinPool(e);
1703 }
1704 }
1705
1706 /**
1707 * Execution continues if there is at least one thread even if
1708 * thread factory fails to create more
1709 */
1710 public void testFailingThreadFactory() throws InterruptedException {
1711 final ExecutorService e =
1712 new CustomTPE(100, 100,
1713 LONG_DELAY_MS, MILLISECONDS,
1714 new LinkedBlockingQueue<Runnable>(),
1715 new FailingThreadFactory());
1716 try {
1717 final int TASKS = 100;
1718 final CountDownLatch done = new CountDownLatch(TASKS);
1719 for (int k = 0; k < TASKS; ++k)
1720 e.execute(new CheckedRunnable() {
1721 public void realRun() {
1722 done.countDown();
1723 }});
1724 assertTrue(done.await(LONG_DELAY_MS, MILLISECONDS));
1725 } finally {
1726 joinPool(e);
1727 }
1728 }
1729
1730 /**
1731 * allowsCoreThreadTimeOut is by default false.
1732 */
1733 public void testAllowsCoreThreadTimeOut() {
1734 ThreadPoolExecutor p = new CustomTPE(2, 2, 1000, MILLISECONDS, new ArrayBlockingQueue<Runnable>(10));
1735 assertFalse(p.allowsCoreThreadTimeOut());
1736 joinPool(p);
1737 }
1738
1739 /**
1740 * allowCoreThreadTimeOut(true) causes idle threads to time out
1741 */
1742 public void testAllowCoreThreadTimeOut_true() throws Exception {
1743 long coreThreadTimeOut = SHORT_DELAY_MS;
1744 final ThreadPoolExecutor p =
1745 new CustomTPE(2, 10,
1746 coreThreadTimeOut, MILLISECONDS,
1747 new ArrayBlockingQueue<Runnable>(10));
1748 final CountDownLatch threadStarted = new CountDownLatch(1);
1749 try {
1750 p.allowCoreThreadTimeOut(true);
1751 p.execute(new CheckedRunnable() {
1752 public void realRun() throws InterruptedException {
1753 threadStarted.countDown();
1754 assertEquals(1, p.getPoolSize());
1755 }});
1756 await(threadStarted);
1757 delay(coreThreadTimeOut);
1758 long startTime = System.nanoTime();
1759 while (p.getPoolSize() > 0
1760 && millisElapsedSince(startTime) < LONG_DELAY_MS)
1761 Thread.yield();
1762 assertTrue(millisElapsedSince(startTime) < LONG_DELAY_MS);
1763 assertEquals(0, p.getPoolSize());
1764 } finally {
1765 joinPool(p);
1766 }
1767 }
1768
1769 /**
1770 * allowCoreThreadTimeOut(false) causes idle threads not to time out
1771 */
1772 public void testAllowCoreThreadTimeOut_false() throws Exception {
1773 long coreThreadTimeOut = SHORT_DELAY_MS;
1774 final ThreadPoolExecutor p =
1775 new CustomTPE(2, 10,
1776 coreThreadTimeOut, MILLISECONDS,
1777 new ArrayBlockingQueue<Runnable>(10));
1778 final CountDownLatch threadStarted = new CountDownLatch(1);
1779 try {
1780 p.allowCoreThreadTimeOut(false);
1781 p.execute(new CheckedRunnable() {
1782 public void realRun() throws InterruptedException {
1783 threadStarted.countDown();
1784 assertTrue(p.getPoolSize() >= 1);
1785 }});
1786 delay(2 * coreThreadTimeOut);
1787 assertTrue(p.getPoolSize() >= 1);
1788 } finally {
1789 joinPool(p);
1790 }
1791 }
1792
1793 }