18f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle/*
28f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle * Written by Doug Lea with assistance from members of JCP JSR-166
38f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle * Expert Group and released to the public domain, as explained at
48f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle * http://creativecommons.org/publicdomain/zero/1.0/
58f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle */
68f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
78f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravlepackage jsr166;
88f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
98f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravleimport static java.util.concurrent.TimeUnit.MILLISECONDS;
10b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniakimport static java.util.concurrent.TimeUnit.NANOSECONDS;
11b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniakimport static java.util.concurrent.TimeUnit.SECONDS;
128e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath
138e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.ArrayList;
14b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniakimport java.util.HashSet;
158e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.List;
168e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.BlockingQueue;
178e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.Callable;
18b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniakimport java.util.concurrent.CancellationException;
198e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.CountDownLatch;
208e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.Delayed;
218e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.ExecutionException;
228e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.Executors;
238e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.ExecutorService;
248e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.Future;
258e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.RejectedExecutionException;
268e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.RejectedExecutionHandler;
278e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.RunnableScheduledFuture;
288e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.ScheduledFuture;
298e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.ScheduledThreadPoolExecutor;
308e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.ThreadFactory;
318e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.ThreadPoolExecutor;
328e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.TimeoutException;
338e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport java.util.concurrent.TimeUnit;
34b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniakimport java.util.concurrent.atomic.AtomicBoolean;
358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravleimport java.util.concurrent.atomic.AtomicInteger;
36b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniakimport java.util.concurrent.atomic.AtomicLong;
378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
388e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport junit.framework.Test;
398e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport junit.framework.TestSuite;
408e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath
418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravlepublic class ScheduledExecutorSubclassTest extends JSR166TestCase {
428e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // android-note: Removed because the CTS runner does a bad job of
438e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // retrying tests that have suite() declarations.
448e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    //
458e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // public static void main(String[] args) {
468e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    //     main(suite(), args);
478e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // }
488e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // public static Test suite() {
49b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak    //     return new TestSuite(ScheduledExecutorSubclassTest.class);
508e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // }
518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    static class CustomTask<V> implements RunnableScheduledFuture<V> {
538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        RunnableScheduledFuture<V> task;
548f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        volatile boolean ran;
558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        CustomTask(RunnableScheduledFuture<V> t) { task = t; }
568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public boolean isPeriodic() { return task.isPeriodic(); }
578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public void run() {
588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            ran = true;
598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            task.run();
608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public long getDelay(TimeUnit unit) { return task.getDelay(unit); }
628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public int compareTo(Delayed t) {
638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            return task.compareTo(((CustomTask)t).task);
648f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
658f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public boolean cancel(boolean mayInterruptIfRunning) {
668f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            return task.cancel(mayInterruptIfRunning);
678f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
688f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public boolean isCancelled() { return task.isCancelled(); }
698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public boolean isDone() { return task.isDone(); }
708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public V get() throws InterruptedException, ExecutionException {
718f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            V v = task.get();
728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(ran);
738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            return v;
748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public V get(long time, TimeUnit unit) throws InterruptedException, ExecutionException, TimeoutException {
768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            V v = task.get(time, unit);
778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(ran);
788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            return v;
798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public class CustomExecutor extends ScheduledThreadPoolExecutor {
838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        protected <V> RunnableScheduledFuture<V> decorateTask(Runnable r, RunnableScheduledFuture<V> task) {
858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            return new CustomTask<V>(task);
868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        protected <V> RunnableScheduledFuture<V> decorateTask(Callable<V> c, RunnableScheduledFuture<V> task) {
898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            return new CustomTask<V>(task);
908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        CustomExecutor(int corePoolSize) { super(corePoolSize); }
928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        CustomExecutor(int corePoolSize, RejectedExecutionHandler handler) {
938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            super(corePoolSize, handler);
948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
968f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        CustomExecutor(int corePoolSize, ThreadFactory threadFactory) {
978f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            super(corePoolSize, threadFactory);
988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        CustomExecutor(int corePoolSize, ThreadFactory threadFactory,
1008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                       RejectedExecutionHandler handler) {
1018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            super(corePoolSize, threadFactory, handler);
1028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
1038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
1078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * execute successfully executes a runnable
1088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
1098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testExecute() throws InterruptedException {
110b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
111b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
112b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch done = new CountDownLatch(1);
113b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final Runnable task = new CheckedRunnable() {
114b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                public void realRun() { done.countDown(); }};
1158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            p.execute(task);
116b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            await(done);
1178f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
1188f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1198f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1208f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
1218f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * delayed schedule of callable successfully executes after delay
1228f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
1238f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSchedule1() throws Exception {
1248f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final CountDownLatch done = new CountDownLatch(1);
125b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
126b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p, done)) {
127b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final long startTime = System.nanoTime();
1288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Callable task = new CheckedCallable<Boolean>() {
1298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                public Boolean realCall() {
1308f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    done.countDown();
1318f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
1328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    return Boolean.TRUE;
1338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }};
1348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Future f = p.schedule(task, timeoutMillis(), MILLISECONDS);
1358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertSame(Boolean.TRUE, f.get());
1368f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
1378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
1388f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1398f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
1418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * delayed schedule of runnable successfully executes after delay
1428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
1438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSchedule3() throws Exception {
144b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
145b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
146b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final long startTime = System.nanoTime();
147b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch done = new CountDownLatch(1);
1488f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Runnable task = new CheckedRunnable() {
1498f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                public void realRun() {
1508f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    done.countDown();
1518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
1528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }};
1538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Future f = p.schedule(task, timeoutMillis(), MILLISECONDS);
1548f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            await(done);
1558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertNull(f.get(LONG_DELAY_MS, MILLISECONDS));
1568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
1578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
1588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
1618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * scheduleAtFixedRate executes runnable after given initial delay
1628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
1638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSchedule4() throws InterruptedException {
164b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
165b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
166b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final long startTime = System.nanoTime();
167b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch done = new CountDownLatch(1);
1688f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Runnable task = new CheckedRunnable() {
1698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                public void realRun() {
1708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    done.countDown();
1718f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
1728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }};
1738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            ScheduledFuture f =
1748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                p.scheduleAtFixedRate(task, timeoutMillis(),
1758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                                      LONG_DELAY_MS, MILLISECONDS);
1768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            await(done);
1778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
1788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            f.cancel(true);
1798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
1808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
1838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * scheduleWithFixedDelay executes runnable after given initial delay
1848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
1858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSchedule5() throws InterruptedException {
186b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
187b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
188b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final long startTime = System.nanoTime();
189b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch done = new CountDownLatch(1);
1908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Runnable task = new CheckedRunnable() {
1918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                public void realRun() {
1928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    done.countDown();
1938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
1948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }};
1958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            ScheduledFuture f =
1968f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                p.scheduleWithFixedDelay(task, timeoutMillis(),
1978f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                                         LONG_DELAY_MS, MILLISECONDS);
1988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            await(done);
1998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
2008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            f.cancel(true);
2018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
2028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    static class RunnableCounter implements Runnable {
2058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        AtomicInteger count = new AtomicInteger(0);
2068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        public void run() { count.getAndIncrement(); }
2078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
210b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * scheduleAtFixedRate executes series of tasks at given rate.
211b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * Eventually, it must hold that:
212b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     *   cycles - 1 <= elapsedMillis/delay < cycles
2138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
2148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testFixedRateSequence() throws InterruptedException {
215b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
216b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
2178e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath            for (int delay = 1; delay <= LONG_DELAY_MS; delay *= 3) {
218b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final long startTime = System.nanoTime();
219b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final int cycles = 8;
2208e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath                final CountDownLatch done = new CountDownLatch(cycles);
221b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final Runnable task = new CheckedRunnable() {
2228e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath                    public void realRun() { done.countDown(); }};
223b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final ScheduledFuture periodicTask =
2248e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath                    p.scheduleAtFixedRate(task, 0, delay, MILLISECONDS);
225b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final int totalDelayMillis = (cycles - 1) * delay;
226b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                await(done, totalDelayMillis + LONG_DELAY_MS);
227b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                periodicTask.cancel(true);
228b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final long elapsedMillis = millisElapsedSince(startTime);
229b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(elapsedMillis >= totalDelayMillis);
230b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                if (elapsedMillis <= cycles * delay)
2318e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath                    return;
232b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                // else retry with longer delay
2338e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath            }
234b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            fail("unexpected execution rate");
2358e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath        }
2368f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2388f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
239b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * scheduleWithFixedDelay executes series of tasks with given period.
240b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * Eventually, it must hold that each task starts at least delay and at
241b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * most 2 * delay after the termination of the previous task.
2428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
2438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testFixedDelaySequence() throws InterruptedException {
244b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
245b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
2468e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath            for (int delay = 1; delay <= LONG_DELAY_MS; delay *= 3) {
247b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final long startTime = System.nanoTime();
248b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final AtomicLong previous = new AtomicLong(startTime);
249b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final AtomicBoolean tryLongerDelay = new AtomicBoolean(false);
250b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final int cycles = 8;
2518e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath                final CountDownLatch done = new CountDownLatch(cycles);
252b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final int d = delay;
253b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final Runnable task = new CheckedRunnable() {
254b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    public void realRun() {
255b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        long now = System.nanoTime();
256b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        long elapsedMillis
257b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                            = NANOSECONDS.toMillis(now - previous.get());
258b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        if (done.getCount() == cycles) { // first execution
259b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                            if (elapsedMillis >= d)
260b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                                tryLongerDelay.set(true);
261b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        } else {
262b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                            assertTrue(elapsedMillis >= d);
263b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                            if (elapsedMillis >= 2 * d)
264b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                                tryLongerDelay.set(true);
265b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        }
266b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        previous.set(now);
267b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        done.countDown();
268b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    }};
269b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final ScheduledFuture periodicTask =
2708e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath                    p.scheduleWithFixedDelay(task, 0, delay, MILLISECONDS);
271b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final int totalDelayMillis = (cycles - 1) * delay;
272b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                await(done, totalDelayMillis + cycles * LONG_DELAY_MS);
273b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                periodicTask.cancel(true);
274b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                final long elapsedMillis = millisElapsedSince(startTime);
275b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(elapsedMillis >= totalDelayMillis);
276b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                if (!tryLongerDelay.get())
2778e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath                    return;
278b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                // else retry with longer delay
2798e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath            }
280b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            fail("unexpected execution rate");
2818e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath        }
2828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
2858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * execute(null) throws NPE
2868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
2878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testExecuteNull() throws InterruptedException {
288b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
289b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
290b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
291b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.execute(null);
292b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
293b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
294b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
2958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2968f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2978f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
2988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * schedule(null) throws NPE
2998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
3008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testScheduleNull() throws InterruptedException {
301b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
302b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
303b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
304b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                TrackedCallable callable = null;
305b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                Future f = p.schedule(callable, SHORT_DELAY_MS, MILLISECONDS);
306b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
307b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
308b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
3098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3108f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
3128f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * execute throws RejectedExecutionException if shutdown
3138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
3148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSchedule1_RejectedExecutionException() {
315b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
316b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
317b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
318b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.shutdown();
319b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.schedule(new NoOpRunnable(),
320b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                           MEDIUM_DELAY_MS, MILLISECONDS);
321b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
322b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (RejectedExecutionException success) {
323b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (SecurityException ok) {}
3248f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
3258f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3268f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3278f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
3288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * schedule throws RejectedExecutionException if shutdown
3298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
3308f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSchedule2_RejectedExecutionException() {
331b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
332b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
333b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
334b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.shutdown();
335b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.schedule(new NoOpCallable(),
336b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                           MEDIUM_DELAY_MS, MILLISECONDS);
337b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
338b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (RejectedExecutionException success) {
339b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (SecurityException ok) {}
3408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
3418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
3448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * schedule callable throws RejectedExecutionException if shutdown
3458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
3468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSchedule3_RejectedExecutionException() {
347b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
348b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
349b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
350b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.shutdown();
351b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.schedule(new NoOpCallable(),
352b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                           MEDIUM_DELAY_MS, MILLISECONDS);
353b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
354b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (RejectedExecutionException success) {
355b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (SecurityException ok) {}
3568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
3578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
3608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * scheduleAtFixedRate throws RejectedExecutionException if shutdown
3618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
3628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testScheduleAtFixedRate1_RejectedExecutionException() {
363b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
364b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
365b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
366b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.shutdown();
367b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.scheduleAtFixedRate(new NoOpRunnable(),
368b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                                      MEDIUM_DELAY_MS, MEDIUM_DELAY_MS, MILLISECONDS);
369b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
370b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (RejectedExecutionException success) {
371b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (SecurityException ok) {}
3728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
3738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
3768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * scheduleWithFixedDelay throws RejectedExecutionException if shutdown
3778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
3788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testScheduleWithFixedDelay1_RejectedExecutionException() {
379b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
380b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
381b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
382b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.shutdown();
383b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.scheduleWithFixedDelay(new NoOpRunnable(),
384b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                                         MEDIUM_DELAY_MS, MEDIUM_DELAY_MS, MILLISECONDS);
385b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
386b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (RejectedExecutionException success) {
387b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (SecurityException ok) {}
3888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
3898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
3928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getActiveCount increases but doesn't overestimate, when a
3938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * thread becomes active
3948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
3958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetActiveCount() throws InterruptedException {
396ed4f365789d43b1961657195df223a19bf4ef20fPrzemyslaw Szczepaniak        final CountDownLatch done = new CountDownLatch(1);
397b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ThreadPoolExecutor p = new CustomExecutor(2);
398b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p, done)) {
399b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadStarted = new CountDownLatch(1);
4008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(0, p.getActiveCount());
4018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            p.execute(new CheckedRunnable() {
4028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                public void realRun() throws InterruptedException {
4038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    threadStarted.countDown();
4048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertEquals(1, p.getActiveCount());
405b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    await(done);
4068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }});
407b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            await(threadStarted);
4088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(1, p.getActiveCount());
4098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
4108f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
4118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
4128f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
4138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getCompletedTaskCount increases, but doesn't overestimate,
4148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * when tasks complete
4158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
4168f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetCompletedTaskCount() throws InterruptedException {
4178f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final ThreadPoolExecutor p = new CustomExecutor(2);
418b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
419b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadStarted = new CountDownLatch(1);
420b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadProceed = new CountDownLatch(1);
421b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadDone = new CountDownLatch(1);
4228f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(0, p.getCompletedTaskCount());
4238f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            p.execute(new CheckedRunnable() {
4248f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                public void realRun() throws InterruptedException {
4258f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    threadStarted.countDown();
4268f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertEquals(0, p.getCompletedTaskCount());
4278f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    threadProceed.await();
4288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    threadDone.countDown();
4298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }});
4308f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            await(threadStarted);
4318f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(0, p.getCompletedTaskCount());
4328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            threadProceed.countDown();
4338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            threadDone.await();
4348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            long startTime = System.nanoTime();
4358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            while (p.getCompletedTaskCount() != 1) {
4368f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                if (millisElapsedSince(startTime) > LONG_DELAY_MS)
4378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    fail("timed out");
4388f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                Thread.yield();
4398f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
4408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
4418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
4428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
4438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
4448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getCorePoolSize returns size given in constructor if not otherwise set
4458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
4468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetCorePoolSize() {
447b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
448b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
449b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(1, p.getCorePoolSize());
450b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
4518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
4528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
4538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
4548f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getLargestPoolSize increases, but doesn't overestimate, when
4558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * multiple threads active
4568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
4578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetLargestPoolSize() throws InterruptedException {
4588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final int THREADS = 3;
459ed4f365789d43b1961657195df223a19bf4ef20fPrzemyslaw Szczepaniak        final CountDownLatch done = new CountDownLatch(1);
460b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ThreadPoolExecutor p = new CustomExecutor(THREADS);
461b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p, done)) {
462b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadsStarted = new CountDownLatch(THREADS);
4638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(0, p.getLargestPoolSize());
4648f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            for (int i = 0; i < THREADS; i++)
4658f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                p.execute(new CheckedRunnable() {
4668f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    public void realRun() throws InterruptedException {
4678f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                        threadsStarted.countDown();
468b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        await(done);
4698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                        assertEquals(THREADS, p.getLargestPoolSize());
4708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    }});
471b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            await(threadsStarted);
4728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(THREADS, p.getLargestPoolSize());
4738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
474b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(THREADS, p.getLargestPoolSize());
4758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
4768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
4778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
4788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getPoolSize increases, but doesn't overestimate, when threads
4798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * become active
4808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
4818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetPoolSize() throws InterruptedException {
482ed4f365789d43b1961657195df223a19bf4ef20fPrzemyslaw Szczepaniak        final CountDownLatch done = new CountDownLatch(1);
483b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ThreadPoolExecutor p = new CustomExecutor(1);
484b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p, done)) {
485b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadStarted = new CountDownLatch(1);
4868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(0, p.getPoolSize());
4878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            p.execute(new CheckedRunnable() {
4888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                public void realRun() throws InterruptedException {
4898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    threadStarted.countDown();
4908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertEquals(1, p.getPoolSize());
491b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    await(done);
4928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }});
493b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            await(threadStarted);
4948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(1, p.getPoolSize());
4958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
4968f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
4978f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
4988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
4998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getTaskCount increases, but doesn't overestimate, when tasks
5008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * submitted
5018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
5028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetTaskCount() throws InterruptedException {
503b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final int TASKS = 3;
504ed4f365789d43b1961657195df223a19bf4ef20fPrzemyslaw Szczepaniak        final CountDownLatch done = new CountDownLatch(1);
505b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ThreadPoolExecutor p = new CustomExecutor(1);
506b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p, done)) {
507b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadStarted = new CountDownLatch(1);
5088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(0, p.getTaskCount());
509b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(0, p.getCompletedTaskCount());
510b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            p.execute(new CheckedRunnable() {
511b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                public void realRun() throws InterruptedException {
512b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    threadStarted.countDown();
513b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    await(done);
514b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                }});
515b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            await(threadStarted);
516b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(1, p.getTaskCount());
517b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(0, p.getCompletedTaskCount());
518b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            for (int i = 0; i < TASKS; i++) {
519b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertEquals(1 + i, p.getTaskCount());
5208f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                p.execute(new CheckedRunnable() {
5218f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    public void realRun() throws InterruptedException {
5228f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                        threadStarted.countDown();
523b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        assertEquals(1 + TASKS, p.getTaskCount());
524b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        await(done);
5258f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    }});
526b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            }
527b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(1 + TASKS, p.getTaskCount());
528b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(0, p.getCompletedTaskCount());
5298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
530b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(1 + TASKS, p.getTaskCount());
531b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(1 + TASKS, p.getCompletedTaskCount());
5328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
5338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
5348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
5358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getThreadFactory returns factory in constructor if not set
5368f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
5378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetThreadFactory() {
538b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ThreadFactory threadFactory = new SimpleThreadFactory();
539b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1, threadFactory);
540b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
541b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertSame(threadFactory, p.getThreadFactory());
542b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
5438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
5448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
5458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
5468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * setThreadFactory sets the thread factory returned by getThreadFactory
5478f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
5488f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSetThreadFactory() {
549b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ThreadFactory threadFactory = new SimpleThreadFactory();
550b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
551b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
552b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            p.setThreadFactory(threadFactory);
553b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertSame(threadFactory, p.getThreadFactory());
554b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
5558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
5568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
5578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
5588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * setThreadFactory(null) throws NPE
5598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
5608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSetThreadFactoryNull() {
561b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
562b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
563b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
564b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                p.setThreadFactory(null);
565b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
566b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
5678f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
5688f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
5698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
5708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
5718f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * isShutdown is false before shutdown, true after
5728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
5738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testIsShutdown() {
574b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
575b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
5768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(p.isShutdown());
5778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            try { p.shutdown(); } catch (SecurityException ok) { return; }
578b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(p.isShutdown());
5798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
5808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
5818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
5828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
5838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * isTerminated is false before termination, true after
5848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
5858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testIsTerminated() throws InterruptedException {
586ed4f365789d43b1961657195df223a19bf4ef20fPrzemyslaw Szczepaniak        final CountDownLatch done = new CountDownLatch(1);
587b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ThreadPoolExecutor p = new CustomExecutor(1);
588b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
589b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadStarted = new CountDownLatch(1);
5908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            p.execute(new CheckedRunnable() {
5918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                public void realRun() throws InterruptedException {
5928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertFalse(p.isTerminated());
5938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    threadStarted.countDown();
594b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    await(done);
5958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }});
596b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            await(threadStarted);
597b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertFalse(p.isTerminated());
5988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(p.isTerminating());
5998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            done.countDown();
6008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            try { p.shutdown(); } catch (SecurityException ok) { return; }
601b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
602b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(p.isTerminated());
6038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
6048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
6058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
6068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
6078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * isTerminating is not true when running or when terminated
6088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
6098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testIsTerminating() throws InterruptedException {
610ed4f365789d43b1961657195df223a19bf4ef20fPrzemyslaw Szczepaniak        final CountDownLatch done = new CountDownLatch(1);
611b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ThreadPoolExecutor p = new CustomExecutor(1);
612b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p)) {
613b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadStarted = new CountDownLatch(1);
6148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(p.isTerminating());
6158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            p.execute(new CheckedRunnable() {
6168f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                public void realRun() throws InterruptedException {
6178f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertFalse(p.isTerminating());
6188f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    threadStarted.countDown();
619b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    await(done);
6208f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }});
621b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            await(threadStarted);
6228f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(p.isTerminating());
6238f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            done.countDown();
6248f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            try { p.shutdown(); } catch (SecurityException ok) { return; }
625b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
626b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(p.isTerminated());
627b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertFalse(p.isTerminating());
6288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
6298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
6308f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
6318f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
6328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getQueue returns the work queue, which contains queued tasks
6338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
6348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetQueue() throws InterruptedException {
6358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final CountDownLatch done = new CountDownLatch(1);
636b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ScheduledThreadPoolExecutor p = new CustomExecutor(1);
637b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p, done)) {
638b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadStarted = new CountDownLatch(1);
6398f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            ScheduledFuture[] tasks = new ScheduledFuture[5];
6408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            for (int i = 0; i < tasks.length; i++) {
6418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                Runnable r = new CheckedRunnable() {
6428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    public void realRun() throws InterruptedException {
6438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                        threadStarted.countDown();
644b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        await(done);
6458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    }};
6468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                tasks[i] = p.schedule(r, 1, MILLISECONDS);
6478f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
648b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            await(threadStarted);
6498f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            BlockingQueue<Runnable> q = p.getQueue();
6508f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(q.contains(tasks[tasks.length - 1]));
6518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(q.contains(tasks[0]));
6528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
6538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
6548f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
6558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
6568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * remove(task) removes queued task, and fails to remove active task
6578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
6588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testRemove() throws InterruptedException {
659ed4f365789d43b1961657195df223a19bf4ef20fPrzemyslaw Szczepaniak        final CountDownLatch done = new CountDownLatch(1);
660b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ScheduledThreadPoolExecutor p = new CustomExecutor(1);
661b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p, done)) {
662b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            ScheduledFuture[] tasks = new ScheduledFuture[5];
663b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch threadStarted = new CountDownLatch(1);
6648f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            for (int i = 0; i < tasks.length; i++) {
6658f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                Runnable r = new CheckedRunnable() {
6668f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    public void realRun() throws InterruptedException {
6678f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                        threadStarted.countDown();
668b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        await(done);
6698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    }};
6708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                tasks[i] = p.schedule(r, 1, MILLISECONDS);
6718f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
672b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            await(threadStarted);
6738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            BlockingQueue<Runnable> q = p.getQueue();
6748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(p.remove((Runnable)tasks[0]));
6758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(q.contains((Runnable)tasks[4]));
6768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(q.contains((Runnable)tasks[3]));
6778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(p.remove((Runnable)tasks[4]));
6788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(p.remove((Runnable)tasks[4]));
6798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(q.contains((Runnable)tasks[4]));
6808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(q.contains((Runnable)tasks[3]));
6818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(p.remove((Runnable)tasks[3]));
6828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(q.contains((Runnable)tasks[3]));
6838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
6848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
6858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
6868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
6878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * purge removes cancelled tasks from the queue
6888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
6898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testPurge() throws InterruptedException {
690b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ScheduledFuture[] tasks = new ScheduledFuture[5];
691b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final Runnable releaser = new Runnable() { public void run() {
692b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            for (ScheduledFuture task : tasks)
693b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                if (task != null) task.cancel(true); }};
694b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
695b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(p, releaser)) {
696b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            for (int i = 0; i < tasks.length; i++)
697b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                tasks[i] = p.schedule(new SmallPossiblyInterruptedRunnable(),
698b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                                      LONG_DELAY_MS, MILLISECONDS);
6998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            int max = tasks.length;
7008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            if (tasks[4].cancel(true)) --max;
7018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            if (tasks[3].cancel(true)) --max;
7028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            // There must eventually be an interference-free point at
7038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            // which purge will not fail. (At worst, when queue is empty.)
7048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            long startTime = System.nanoTime();
7058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            do {
7068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                p.purge();
7078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                long count = p.getTaskCount();
7088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                if (count == max)
7098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    return;
710b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } while (millisElapsedSince(startTime) < LONG_DELAY_MS);
7118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            fail("Purge failed to remove cancelled tasks");
7128f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
7138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
7148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
7158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
716b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * shutdownNow returns a list containing tasks that were not run,
717b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * and those tasks are drained from the queue
7188f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
719b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak    public void testShutdownNow() throws InterruptedException {
720b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final int poolSize = 2;
721b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final int count = 5;
722b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final AtomicInteger ran = new AtomicInteger(0);
723b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(poolSize);
724b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CountDownLatch threadsStarted = new CountDownLatch(poolSize);
725b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        Runnable waiter = new CheckedRunnable() { public void realRun() {
726b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            threadsStarted.countDown();
727b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
728b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                MILLISECONDS.sleep(2 * LONG_DELAY_MS);
729b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (InterruptedException success) {}
730b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            ran.getAndIncrement();
731b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }};
732b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        for (int i = 0; i < count; i++)
733b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            p.execute(waiter);
734b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        await(threadsStarted);
735b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(poolSize, p.getActiveCount());
736b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(0, p.getCompletedTaskCount());
737b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final List<Runnable> queuedTasks;
7388f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        try {
739b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            queuedTasks = p.shutdownNow();
7408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        } catch (SecurityException ok) {
741b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            return; // Allowed in case test doesn't have privs
7428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
743b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.isShutdown());
744b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.getQueue().isEmpty());
745b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(count - poolSize, queuedTasks.size());
746b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
747b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.isTerminated());
748b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(poolSize, ran.get());
749b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(poolSize, p.getCompletedTaskCount());
7508f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
7518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
7528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
753b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * shutdownNow returns a list containing tasks that were not run,
754b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * and those tasks are drained from the queue
7558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
756b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak    public void testShutdownNow_delayedTasks() throws InterruptedException {
757b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(1);
758b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        List<ScheduledFuture> tasks = new ArrayList<>();
759b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        for (int i = 0; i < 3; i++) {
760b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            Runnable r = new NoOpRunnable();
761b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            tasks.add(p.schedule(r, 9, SECONDS));
762b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            tasks.add(p.scheduleAtFixedRate(r, 9, 9, SECONDS));
763b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            tasks.add(p.scheduleWithFixedDelay(r, 9, 9, SECONDS));
764b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
765b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        if (testImplementationDetails)
766b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(new HashSet(tasks), new HashSet(p.getQueue()));
767b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final List<Runnable> queuedTasks;
768b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try {
769b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            queuedTasks = p.shutdownNow();
770b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        } catch (SecurityException ok) {
771b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            return; // Allowed in case test doesn't have privs
7728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
7738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        assertTrue(p.isShutdown());
774b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.getQueue().isEmpty());
775b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        if (testImplementationDetails)
776b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(new HashSet(tasks), new HashSet(queuedTasks));
777b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(tasks.size(), queuedTasks.size());
7788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        for (ScheduledFuture task : tasks) {
779b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertFalse(((CustomTask)task).ran);
780b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertFalse(task.isDone());
7818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertFalse(task.isCancelled());
7828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
783b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
7848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        assertTrue(p.isTerminated());
7858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
7868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
7878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
788b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * By default, periodic tasks are cancelled at shutdown.
789b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * By default, delayed tasks keep running after shutdown.
790b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * Check that changing the default values work:
791b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * - setExecuteExistingDelayedTasksAfterShutdownPolicy
792b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak     * - setContinueExistingPeriodicTasksAfterShutdownPolicy
7938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
794b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak    public void testShutdown_cancellation() throws Exception {
795b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        Boolean[] allBooleans = { null, Boolean.FALSE, Boolean.TRUE };
796b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        for (Boolean policy : allBooleans)
797b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak    {
798b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final int poolSize = 2;
799b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CustomExecutor p = new CustomExecutor(poolSize);
800b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final boolean effectiveDelayedPolicy = (policy != Boolean.FALSE);
801b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final boolean effectivePeriodicPolicy = (policy == Boolean.TRUE);
802b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final boolean effectiveRemovePolicy = (policy == Boolean.TRUE);
803b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        if (policy != null) {
804b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            p.setExecuteExistingDelayedTasksAfterShutdownPolicy(policy);
805b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            p.setContinueExistingPeriodicTasksAfterShutdownPolicy(policy);
806b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            p.setRemoveOnCancelPolicy(policy);
807b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
808b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(effectiveDelayedPolicy,
809b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                     p.getExecuteExistingDelayedTasksAfterShutdownPolicy());
810b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(effectivePeriodicPolicy,
811b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                     p.getContinueExistingPeriodicTasksAfterShutdownPolicy());
812b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(effectiveRemovePolicy,
813b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                     p.getRemoveOnCancelPolicy());
814b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        // Strategy: Wedge the pool with poolSize "blocker" threads
815b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final AtomicInteger ran = new AtomicInteger(0);
816b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CountDownLatch poolBlocked = new CountDownLatch(poolSize);
817b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CountDownLatch unblock = new CountDownLatch(1);
818b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CountDownLatch periodicLatch1 = new CountDownLatch(2);
819b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CountDownLatch periodicLatch2 = new CountDownLatch(2);
820b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        Runnable task = new CheckedRunnable() { public void realRun()
821b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                                                    throws InterruptedException {
822b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            poolBlocked.countDown();
823b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(unblock.await(LONG_DELAY_MS, MILLISECONDS));
824b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            ran.getAndIncrement();
825b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }};
826b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        List<Future<?>> blockers = new ArrayList<>();
827b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        List<Future<?>> periodics = new ArrayList<>();
828b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        List<Future<?>> delayeds = new ArrayList<>();
829b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        for (int i = 0; i < poolSize; i++)
830b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            blockers.add(p.submit(task));
831b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(poolBlocked.await(LONG_DELAY_MS, MILLISECONDS));
832b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak
833b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        periodics.add(p.scheduleAtFixedRate(countDowner(periodicLatch1),
834b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                                            1, 1, MILLISECONDS));
835b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        periodics.add(p.scheduleWithFixedDelay(countDowner(periodicLatch2),
836b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                                               1, 1, MILLISECONDS));
837b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        delayeds.add(p.schedule(task, 1, MILLISECONDS));
838b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak
839b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.getQueue().containsAll(periodics));
840b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.getQueue().containsAll(delayeds));
8418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        try { p.shutdown(); } catch (SecurityException ok) { return; }
8428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        assertTrue(p.isShutdown());
843b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertFalse(p.isTerminated());
844b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        for (Future<?> periodic : periodics) {
845b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(effectivePeriodicPolicy ^ periodic.isCancelled());
846b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(effectivePeriodicPolicy ^ periodic.isDone());
847b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
848b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        for (Future<?> delayed : delayeds) {
849b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(effectiveDelayedPolicy ^ delayed.isCancelled());
850b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(effectiveDelayedPolicy ^ delayed.isDone());
851b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
852b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        if (testImplementationDetails) {
853b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(effectivePeriodicPolicy,
854b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                         p.getQueue().containsAll(periodics));
855b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(effectiveDelayedPolicy,
856b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                         p.getQueue().containsAll(delayeds));
857b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        }
858b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        // Release all pool threads
859b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        unblock.countDown();
860b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak
861b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        for (Future<?> delayed : delayeds) {
862b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            if (effectiveDelayedPolicy) {
863b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertNull(delayed.get());
864b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            }
8658f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
866b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        if (effectivePeriodicPolicy) {
867b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(periodicLatch1.await(LONG_DELAY_MS, MILLISECONDS));
868b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(periodicLatch2.await(LONG_DELAY_MS, MILLISECONDS));
869b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            for (Future<?> periodic : periodics) {
870b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(periodic.cancel(false));
871b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(periodic.isCancelled());
872b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(periodic.isDone());
873b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            }
8748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
875b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
876b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertTrue(p.isTerminated());
877b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        assertEquals(2 + (effectiveDelayedPolicy ? 1 : 0), ran.get());
878b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak    }}
8798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
8808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
8818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * completed submit of callable returns result
8828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
8838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSubmitCallable() throws Exception {
884b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
885b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
8868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Future<String> future = e.submit(new StringTask());
8878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            String result = future.get();
8888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertSame(TEST_STRING, result);
8898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
8908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
8918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
8928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
8938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * completed submit of runnable returns successfully
8948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
8958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSubmitRunnable() throws Exception {
896b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
897b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
8988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Future<?> future = e.submit(new NoOpRunnable());
8998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            future.get();
9008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(future.isDone());
9018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
9028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
9038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
9048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
9058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * completed submit of (runnable, result) returns result
9068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
9078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testSubmitRunnable2() throws Exception {
908b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
909b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
9108f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Future<String> future = e.submit(new NoOpRunnable(), TEST_STRING);
9118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            String result = future.get();
9128f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertSame(TEST_STRING, result);
9138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
9148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
9158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
9168f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
9178f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * invokeAny(null) throws NPE
9188f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
9198f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAny1() throws Exception {
920b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
921b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
922b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
923b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAny(null);
924b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
925b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
9268f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
9278f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
9288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
9298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
9308f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * invokeAny(empty collection) throws IAE
9318f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
9328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAny2() throws Exception {
933b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
934b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
935b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
936b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAny(new ArrayList<Callable<String>>());
937b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
938b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (IllegalArgumentException success) {}
9398f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
9408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
9418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
9428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
9438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * invokeAny(c) throws NPE if c has null elements
9448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
9458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAny3() throws Exception {
946b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final CountDownLatch latch = new CountDownLatch(1);
947b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
948b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
949b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
950b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(latchAwaitingStringTask(latch));
951b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(null);
952b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
953b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAny(l);
954b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
955b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
9568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            latch.countDown();
9578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
9588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
9598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
9608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
9618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * invokeAny(c) throws ExecutionException if no task completes
9628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
9638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAny4() throws Exception {
964b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
965b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
966b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
967b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(new NPETask());
968b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
969b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAny(l);
970b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
971b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (ExecutionException success) {
972b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(success.getCause() instanceof NullPointerException);
973b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            }
9748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
9758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
9768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
9778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
9788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * invokeAny(c) returns result of some task
9798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
9808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAny5() throws Exception {
981b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
982b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
9838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            List<Callable<String>> l = new ArrayList<Callable<String>>();
9848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            l.add(new StringTask());
9858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            l.add(new StringTask());
9868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            String result = e.invokeAny(l);
9878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertSame(TEST_STRING, result);
9888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
9898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
9908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
9918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
9928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * invokeAll(null) throws NPE
9938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
9948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAll1() throws Exception {
995b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
996b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
997b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
998b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAll(null);
999b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1000b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
10018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
10028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
10038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
10048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
10058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * invokeAll(empty collection) returns empty collection
10068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
10078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAll2() throws Exception {
1008b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1009b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
10108f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            List<Future<String>> r = e.invokeAll(new ArrayList<Callable<String>>());
10118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(r.isEmpty());
10128f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
10138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
10148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
10158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
10168f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * invokeAll(c) throws NPE if c has null elements
10178f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
10188f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAll3() throws Exception {
1019b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1020b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1021b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
1022b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(new StringTask());
1023b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(null);
1024b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1025b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAll(l);
1026b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1027b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
10288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
10298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
10308f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
10318f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
10328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * get of invokeAll(c) throws exception on failed task
10338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
10348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAll4() throws Exception {
1035b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1036b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1037b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
1038b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(new NPETask());
1039b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Future<String>> futures = e.invokeAll(l);
1040b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(1, futures.size());
1041b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1042b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                futures.get(0).get();
1043b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1044b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (ExecutionException success) {
1045b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(success.getCause() instanceof NullPointerException);
1046b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            }
10478f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
10488f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
10498f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
10508f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
10518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * invokeAll(c) returns results of all completed tasks
10528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
10538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testInvokeAll5() throws Exception {
1054b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1055b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
10568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            List<Callable<String>> l = new ArrayList<Callable<String>>();
10578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            l.add(new StringTask());
10588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            l.add(new StringTask());
10598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            List<Future<String>> futures = e.invokeAll(l);
10608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(2, futures.size());
10618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            for (Future<String> future : futures)
10628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                assertSame(TEST_STRING, future.get());
10638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
10648f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
10658f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
10668f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
10678f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAny(null) throws NPE
10688f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
10698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAny1() throws Exception {
1070b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1071b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1072b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1073b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAny(null, MEDIUM_DELAY_MS, MILLISECONDS);
1074b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1075b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
10768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
10778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
10788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
10798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
10808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAny(,,null) throws NPE
10818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
10828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAnyNullTimeUnit() throws Exception {
1083b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1084b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1085b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
1086b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(new StringTask());
1087b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1088b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAny(l, MEDIUM_DELAY_MS, null);
1089b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1090b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
10918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
10928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
10938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
10948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
10958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAny(empty collection) throws IAE
10968f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
10978f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAny2() throws Exception {
1098b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1099b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1100b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1101b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAny(new ArrayList<Callable<String>>(), MEDIUM_DELAY_MS, MILLISECONDS);
1102b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1103b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (IllegalArgumentException success) {}
11048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
11058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
11068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
11078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
11088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAny(c) throws NPE if c has null elements
11098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
11108f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAny3() throws Exception {
11118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        CountDownLatch latch = new CountDownLatch(1);
1112b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1113b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1114b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
1115b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(latchAwaitingStringTask(latch));
1116b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(null);
1117b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1118b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
1119b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1120b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
11218f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            latch.countDown();
11228f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
11238f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
11248f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
11258f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
11268f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAny(c) throws ExecutionException if no task completes
11278f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
11288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAny4() throws Exception {
1129b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1130b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1131b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            long startTime = System.nanoTime();
1132b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
1133b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(new NPETask());
1134b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1135b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAny(l, LONG_DELAY_MS, MILLISECONDS);
1136b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1137b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (ExecutionException success) {
1138b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(success.getCause() instanceof NullPointerException);
1139b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            }
1140b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(millisElapsedSince(startTime) < LONG_DELAY_MS);
11418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
11428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
11438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
11448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
11458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAny(c) returns result of some task
11468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
11478f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAny5() throws Exception {
1148b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1149b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1150b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            long startTime = System.nanoTime();
11518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            List<Callable<String>> l = new ArrayList<Callable<String>>();
11528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            l.add(new StringTask());
11538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            l.add(new StringTask());
1154b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            String result = e.invokeAny(l, LONG_DELAY_MS, MILLISECONDS);
11558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertSame(TEST_STRING, result);
1156b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertTrue(millisElapsedSince(startTime) < LONG_DELAY_MS);
11578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
11588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
11598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
11608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
11618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAll(null) throws NPE
11628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
11638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAll1() throws Exception {
1164b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1165b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1166b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1167b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAll(null, MEDIUM_DELAY_MS, MILLISECONDS);
1168b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1169b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
11708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
11718f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
11728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
11738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
11748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAll(,,null) throws NPE
11758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
11768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAllNullTimeUnit() throws Exception {
1177b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1178b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1179b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
1180b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(new StringTask());
1181b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1182b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAll(l, MEDIUM_DELAY_MS, null);
1183b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1184b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
11858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
11868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
11878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
11888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
11898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAll(empty collection) returns empty collection
11908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
11918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAll2() throws Exception {
1192b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1193b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
11948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            List<Future<String>> r = e.invokeAll(new ArrayList<Callable<String>>(), MEDIUM_DELAY_MS, MILLISECONDS);
11958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertTrue(r.isEmpty());
11968f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
11978f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
11988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
11998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
12008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAll(c) throws NPE if c has null elements
12018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
12028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAll3() throws Exception {
1203b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1204b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1205b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
1206b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(new StringTask());
1207b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(null);
1208b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1209b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
1210b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1211b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (NullPointerException success) {}
12128f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
12138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
12148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
12158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
12168f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * get of element of invokeAll(c) throws exception on failed task
12178f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
12188f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAll4() throws Exception {
1219b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1220b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
1221b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Callable<String>> l = new ArrayList<Callable<String>>();
1222b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            l.add(new NPETask());
1223b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            List<Future<String>> futures =
1224b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
1225b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            assertEquals(1, futures.size());
1226b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try {
1227b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                futures.get(0).get();
1228b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                shouldThrow();
1229b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            } catch (ExecutionException success) {
1230b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(success.getCause() instanceof NullPointerException);
1231b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            }
12328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
12338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
12348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
12358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
12368f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAll(c) returns results of all completed tasks
12378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
12388f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAll5() throws Exception {
1239b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        final ExecutorService e = new CustomExecutor(2);
1240b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        try (PoolCleaner cleaner = cleaner(e)) {
12418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            List<Callable<String>> l = new ArrayList<Callable<String>>();
12428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            l.add(new StringTask());
12438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            l.add(new StringTask());
12448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            List<Future<String>> futures =
1245b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                e.invokeAll(l, LONG_DELAY_MS, MILLISECONDS);
12468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            assertEquals(2, futures.size());
12478f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            for (Future<String> future : futures)
12488f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                assertSame(TEST_STRING, future.get());
12498f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
12508f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
12518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
12528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
12538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed invokeAll(c) cancels tasks not completed by timeout
12548f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
12558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testTimedInvokeAll6() throws Exception {
1256b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak        for (long timeout = timeoutMillis();;) {
1257b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final CountDownLatch done = new CountDownLatch(1);
1258b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final Callable<String> waiter = new CheckedCallable<String>() {
1259b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                public String realCall() {
1260b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    try { done.await(LONG_DELAY_MS, MILLISECONDS); }
1261b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    catch (InterruptedException ok) {}
1262b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    return "1"; }};
1263b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            final ExecutorService p = new CustomExecutor(2);
1264b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            try (PoolCleaner cleaner = cleaner(p, done)) {
1265b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                List<Callable<String>> tasks = new ArrayList<>();
1266b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                tasks.add(new StringTask("0"));
1267b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                tasks.add(waiter);
1268b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                tasks.add(new StringTask("2"));
1269b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                long startTime = System.nanoTime();
1270b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                List<Future<String>> futures =
1271b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    p.invokeAll(tasks, timeout, MILLISECONDS);
1272b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertEquals(tasks.size(), futures.size());
1273b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(millisElapsedSince(startTime) >= timeout);
1274b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                for (Future future : futures)
1275b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    assertTrue(future.isDone());
1276b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                assertTrue(futures.get(1).isCancelled());
1277b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                try {
1278b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    assertEquals("0", futures.get(0).get());
1279b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    assertEquals("2", futures.get(2).get());
1280b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    break;
1281b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                } catch (CancellationException retryWithLongerTimeout) {
1282b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    timeout *= 2;
1283b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                    if (timeout >= LONG_DELAY_MS / 2)
1284b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                        fail("expected exactly one task to be cancelled");
1285b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak                }
1286b8b75116273ecfdb8ffdd1869b1c0dd04570a95ePrzemyslaw Szczepaniak            }
12878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
12888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
12898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
12908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle}
1291