Home | History | Annotate | Download | only in jsr166
      1 /*
      2  * Written by Doug Lea with assistance from members of JCP JSR-166
      3  * Expert Group and released to the public domain, as explained at
      4  * http://creativecommons.org/publicdomain/zero/1.0/
      5  * Other contributors include Andrew Wright, Jeffrey Hayes,
      6  * Pat Fisher, Mike Judd.
      7  */
      8 
      9 package jsr166;
     10 
     11 import junit.framework.*;
     12 import java.util.*;
     13 import java.util.concurrent.*;
     14 import static java.util.concurrent.TimeUnit.MILLISECONDS;
     15 import java.util.concurrent.atomic.AtomicInteger;
     16 
     17 public class ScheduledExecutorTest extends JSR166TestCase {
     18 
     19     /**
     20      * execute successfully executes a runnable
     21      */
     22     public void testExecute() throws InterruptedException {
     23         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
     24         final CountDownLatch done = new CountDownLatch(1);
     25         final Runnable task = new CheckedRunnable() {
     26             public void realRun() {
     27                 done.countDown();
     28             }};
     29         try {
     30             p.execute(task);
     31             assertTrue(done.await(SMALL_DELAY_MS, MILLISECONDS));
     32         } finally {
     33             joinPool(p);
     34         }
     35     }
     36 
     37     /**
     38      * delayed schedule of callable successfully executes after delay
     39      */
     40     public void testSchedule1() throws Exception {
     41         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
     42         final long startTime = System.nanoTime();
     43         final CountDownLatch done = new CountDownLatch(1);
     44         try {
     45             Callable task = new CheckedCallable<Boolean>() {
     46                 public Boolean realCall() {
     47                     done.countDown();
     48                     assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
     49                     return Boolean.TRUE;
     50                 }};
     51             Future f = p.schedule(task, timeoutMillis(), MILLISECONDS);
     52             assertSame(Boolean.TRUE, f.get());
     53             assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
     54             assertTrue(done.await(0L, MILLISECONDS));
     55         } finally {
     56             joinPool(p);
     57         }
     58     }
     59 
     60     /**
     61      * delayed schedule of runnable successfully executes after delay
     62      */
     63     public void testSchedule3() throws Exception {
     64         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
     65         final long startTime = System.nanoTime();
     66         final CountDownLatch done = new CountDownLatch(1);
     67         try {
     68             Runnable task = new CheckedRunnable() {
     69                 public void realRun() {
     70                     done.countDown();
     71                     assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
     72                 }};
     73             Future f = p.schedule(task, timeoutMillis(), MILLISECONDS);
     74             await(done);
     75             assertNull(f.get(LONG_DELAY_MS, MILLISECONDS));
     76             assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
     77         } finally {
     78             joinPool(p);
     79         }
     80     }
     81 
     82     /**
     83      * scheduleAtFixedRate executes runnable after given initial delay
     84      */
     85     public void testSchedule4() throws Exception {
     86         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
     87         final long startTime = System.nanoTime();
     88         final CountDownLatch done = new CountDownLatch(1);
     89         try {
     90             Runnable task = new CheckedRunnable() {
     91                 public void realRun() {
     92                     done.countDown();
     93                     assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
     94                 }};
     95             ScheduledFuture f =
     96                 p.scheduleAtFixedRate(task, timeoutMillis(),
     97                                       LONG_DELAY_MS, MILLISECONDS);
     98             await(done);
     99             assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
    100             f.cancel(true);
    101         } finally {
    102             joinPool(p);
    103         }
    104     }
    105 
    106     /**
    107      * scheduleWithFixedDelay executes runnable after given initial delay
    108      */
    109     public void testSchedule5() throws Exception {
    110         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    111         final long startTime = System.nanoTime();
    112         final CountDownLatch done = new CountDownLatch(1);
    113         try {
    114             Runnable task = new CheckedRunnable() {
    115                 public void realRun() {
    116                     done.countDown();
    117                     assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
    118                 }};
    119             ScheduledFuture f =
    120                 p.scheduleWithFixedDelay(task, timeoutMillis(),
    121                                          LONG_DELAY_MS, MILLISECONDS);
    122             await(done);
    123             assertTrue(millisElapsedSince(startTime) >= timeoutMillis());
    124             f.cancel(true);
    125         } finally {
    126             joinPool(p);
    127         }
    128     }
    129 
    130     static class RunnableCounter implements Runnable {
    131         AtomicInteger count = new AtomicInteger(0);
    132         public void run() { count.getAndIncrement(); }
    133     }
    134 
    135     /**
    136      * scheduleAtFixedRate executes series of tasks at given rate
    137      */
    138     public void testFixedRateSequence() throws InterruptedException {
    139         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    140         RunnableCounter counter = new RunnableCounter();
    141         ScheduledFuture h =
    142             p.scheduleAtFixedRate(counter, 0, 1, MILLISECONDS);
    143         delay(SMALL_DELAY_MS);
    144         h.cancel(true);
    145         int c = counter.count.get();
    146         // By time scaling conventions, we must have at least
    147         // an execution per SHORT delay, but no more than one SHORT more
    148         assertTrue(c >= SMALL_DELAY_MS / SHORT_DELAY_MS);
    149         assertTrue(c <= SMALL_DELAY_MS + SHORT_DELAY_MS);
    150         joinPool(p);
    151     }
    152 
    153     /**
    154      * scheduleWithFixedDelay executes series of tasks with given period
    155      */
    156     public void testFixedDelaySequence() throws InterruptedException {
    157         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    158         RunnableCounter counter = new RunnableCounter();
    159         ScheduledFuture h =
    160             p.scheduleWithFixedDelay(counter, 0, 1, MILLISECONDS);
    161         delay(SMALL_DELAY_MS);
    162         h.cancel(true);
    163         int c = counter.count.get();
    164         assertTrue(c >= SMALL_DELAY_MS / SHORT_DELAY_MS);
    165         assertTrue(c <= SMALL_DELAY_MS + SHORT_DELAY_MS);
    166         joinPool(p);
    167     }
    168 
    169     /**
    170      * execute(null) throws NPE
    171      */
    172     public void testExecuteNull() throws InterruptedException {
    173         ScheduledThreadPoolExecutor se = null;
    174         try {
    175             se = new ScheduledThreadPoolExecutor(1);
    176             se.execute(null);
    177             shouldThrow();
    178         } catch (NullPointerException success) {}
    179 
    180         joinPool(se);
    181     }
    182 
    183     /**
    184      * schedule(null) throws NPE
    185      */
    186     public void testScheduleNull() throws InterruptedException {
    187         ScheduledThreadPoolExecutor se = new ScheduledThreadPoolExecutor(1);
    188         try {
    189             TrackedCallable callable = null;
    190             Future f = se.schedule(callable, SHORT_DELAY_MS, MILLISECONDS);
    191             shouldThrow();
    192         } catch (NullPointerException success) {}
    193         joinPool(se);
    194     }
    195 
    196     /**
    197      * execute throws RejectedExecutionException if shutdown
    198      */
    199     public void testSchedule1_RejectedExecutionException() throws InterruptedException {
    200         ScheduledThreadPoolExecutor se = new ScheduledThreadPoolExecutor(1);
    201         try {
    202             se.shutdown();
    203             se.schedule(new NoOpRunnable(),
    204                         MEDIUM_DELAY_MS, MILLISECONDS);
    205             shouldThrow();
    206         } catch (RejectedExecutionException success) {
    207         } catch (SecurityException ok) {
    208         }
    209 
    210         joinPool(se);
    211     }
    212 
    213     /**
    214      * schedule throws RejectedExecutionException if shutdown
    215      */
    216     public void testSchedule2_RejectedExecutionException() throws InterruptedException {
    217         ScheduledThreadPoolExecutor se = new ScheduledThreadPoolExecutor(1);
    218         try {
    219             se.shutdown();
    220             se.schedule(new NoOpCallable(),
    221                         MEDIUM_DELAY_MS, MILLISECONDS);
    222             shouldThrow();
    223         } catch (RejectedExecutionException success) {
    224         } catch (SecurityException ok) {
    225         }
    226         joinPool(se);
    227     }
    228 
    229     /**
    230      * schedule callable throws RejectedExecutionException if shutdown
    231      */
    232     public void testSchedule3_RejectedExecutionException() throws InterruptedException {
    233         ScheduledThreadPoolExecutor se = new ScheduledThreadPoolExecutor(1);
    234         try {
    235             se.shutdown();
    236             se.schedule(new NoOpCallable(),
    237                         MEDIUM_DELAY_MS, MILLISECONDS);
    238             shouldThrow();
    239         } catch (RejectedExecutionException success) {
    240         } catch (SecurityException ok) {
    241         }
    242         joinPool(se);
    243     }
    244 
    245     /**
    246      * scheduleAtFixedRate throws RejectedExecutionException if shutdown
    247      */
    248     public void testScheduleAtFixedRate1_RejectedExecutionException() throws InterruptedException {
    249         ScheduledThreadPoolExecutor se = new ScheduledThreadPoolExecutor(1);
    250         try {
    251             se.shutdown();
    252             se.scheduleAtFixedRate(new NoOpRunnable(),
    253                                    MEDIUM_DELAY_MS, MEDIUM_DELAY_MS, MILLISECONDS);
    254             shouldThrow();
    255         } catch (RejectedExecutionException success) {
    256         } catch (SecurityException ok) {
    257         }
    258         joinPool(se);
    259     }
    260 
    261     /**
    262      * scheduleWithFixedDelay throws RejectedExecutionException if shutdown
    263      */
    264     public void testScheduleWithFixedDelay1_RejectedExecutionException() throws InterruptedException {
    265         ScheduledThreadPoolExecutor se = new ScheduledThreadPoolExecutor(1);
    266         try {
    267             se.shutdown();
    268             se.scheduleWithFixedDelay(new NoOpRunnable(),
    269                                       MEDIUM_DELAY_MS, MEDIUM_DELAY_MS, MILLISECONDS);
    270             shouldThrow();
    271         } catch (RejectedExecutionException success) {
    272         } catch (SecurityException ok) {
    273         }
    274         joinPool(se);
    275     }
    276 
    277     /**
    278      * getActiveCount increases but doesn't overestimate, when a
    279      * thread becomes active
    280      */
    281     public void testGetActiveCount() throws InterruptedException {
    282         final ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(2);
    283         final CountDownLatch threadStarted = new CountDownLatch(1);
    284         final CountDownLatch done = new CountDownLatch(1);
    285         try {
    286             assertEquals(0, p.getActiveCount());
    287             p.execute(new CheckedRunnable() {
    288                 public void realRun() throws InterruptedException {
    289                     threadStarted.countDown();
    290                     assertEquals(1, p.getActiveCount());
    291                     done.await();
    292                 }});
    293             assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
    294             assertEquals(1, p.getActiveCount());
    295         } finally {
    296             done.countDown();
    297             joinPool(p);
    298         }
    299     }
    300 
    301     /**
    302      * getCompletedTaskCount increases, but doesn't overestimate,
    303      * when tasks complete
    304      */
    305     public void testGetCompletedTaskCount() throws InterruptedException {
    306         final ThreadPoolExecutor p = new ScheduledThreadPoolExecutor(2);
    307         final CountDownLatch threadStarted = new CountDownLatch(1);
    308         final CountDownLatch threadProceed = new CountDownLatch(1);
    309         final CountDownLatch threadDone = new CountDownLatch(1);
    310         try {
    311             assertEquals(0, p.getCompletedTaskCount());
    312             p.execute(new CheckedRunnable() {
    313                 public void realRun() throws InterruptedException {
    314                     threadStarted.countDown();
    315                     assertEquals(0, p.getCompletedTaskCount());
    316                     threadProceed.await();
    317                     threadDone.countDown();
    318                 }});
    319             await(threadStarted);
    320             assertEquals(0, p.getCompletedTaskCount());
    321             threadProceed.countDown();
    322             threadDone.await();
    323             long startTime = System.nanoTime();
    324             while (p.getCompletedTaskCount() != 1) {
    325                 if (millisElapsedSince(startTime) > LONG_DELAY_MS)
    326                     fail("timed out");
    327                 Thread.yield();
    328             }
    329         } finally {
    330             joinPool(p);
    331         }
    332     }
    333 
    334     /**
    335      * getCorePoolSize returns size given in constructor if not otherwise set
    336      */
    337     public void testGetCorePoolSize() throws InterruptedException {
    338         ThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    339         assertEquals(1, p.getCorePoolSize());
    340         joinPool(p);
    341     }
    342 
    343     /**
    344      * getLargestPoolSize increases, but doesn't overestimate, when
    345      * multiple threads active
    346      */
    347     public void testGetLargestPoolSize() throws InterruptedException {
    348         final int THREADS = 3;
    349         final ThreadPoolExecutor p = new ScheduledThreadPoolExecutor(THREADS);
    350         final CountDownLatch threadsStarted = new CountDownLatch(THREADS);
    351         final CountDownLatch done = new CountDownLatch(1);
    352         try {
    353             assertEquals(0, p.getLargestPoolSize());
    354             for (int i = 0; i < THREADS; i++)
    355                 p.execute(new CheckedRunnable() {
    356                     public void realRun() throws InterruptedException {
    357                         threadsStarted.countDown();
    358                         done.await();
    359                         assertEquals(THREADS, p.getLargestPoolSize());
    360                     }});
    361             assertTrue(threadsStarted.await(SMALL_DELAY_MS, MILLISECONDS));
    362             assertEquals(THREADS, p.getLargestPoolSize());
    363         } finally {
    364             done.countDown();
    365             joinPool(p);
    366             assertEquals(THREADS, p.getLargestPoolSize());
    367         }
    368     }
    369 
    370     /**
    371      * getPoolSize increases, but doesn't overestimate, when threads
    372      * become active
    373      */
    374     public void testGetPoolSize() throws InterruptedException {
    375         final ThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    376         final CountDownLatch threadStarted = new CountDownLatch(1);
    377         final CountDownLatch done = new CountDownLatch(1);
    378         try {
    379             assertEquals(0, p.getPoolSize());
    380             p.execute(new CheckedRunnable() {
    381                 public void realRun() throws InterruptedException {
    382                     threadStarted.countDown();
    383                     assertEquals(1, p.getPoolSize());
    384                     done.await();
    385                 }});
    386             assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
    387             assertEquals(1, p.getPoolSize());
    388         } finally {
    389             done.countDown();
    390             joinPool(p);
    391         }
    392     }
    393 
    394     /**
    395      * getTaskCount increases, but doesn't overestimate, when tasks
    396      * submitted
    397      */
    398     public void testGetTaskCount() throws InterruptedException {
    399         final ThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    400         final CountDownLatch threadStarted = new CountDownLatch(1);
    401         final CountDownLatch done = new CountDownLatch(1);
    402         final int TASKS = 5;
    403         try {
    404             assertEquals(0, p.getTaskCount());
    405             for (int i = 0; i < TASKS; i++)
    406                 p.execute(new CheckedRunnable() {
    407                     public void realRun() throws InterruptedException {
    408                         threadStarted.countDown();
    409                         done.await();
    410                     }});
    411             assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
    412             assertEquals(TASKS, p.getTaskCount());
    413         } finally {
    414             done.countDown();
    415             joinPool(p);
    416         }
    417     }
    418 
    419     /**
    420      * getThreadFactory returns factory in constructor if not set
    421      */
    422     public void testGetThreadFactory() throws InterruptedException {
    423         ThreadFactory tf = new SimpleThreadFactory();
    424         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1, tf);
    425         assertSame(tf, p.getThreadFactory());
    426         joinPool(p);
    427     }
    428 
    429     /**
    430      * setThreadFactory sets the thread factory returned by getThreadFactory
    431      */
    432     public void testSetThreadFactory() throws InterruptedException {
    433         ThreadFactory tf = new SimpleThreadFactory();
    434         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    435         p.setThreadFactory(tf);
    436         assertSame(tf, p.getThreadFactory());
    437         joinPool(p);
    438     }
    439 
    440     /**
    441      * setThreadFactory(null) throws NPE
    442      */
    443     public void testSetThreadFactoryNull() throws InterruptedException {
    444         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    445         try {
    446             p.setThreadFactory(null);
    447             shouldThrow();
    448         } catch (NullPointerException success) {
    449         } finally {
    450             joinPool(p);
    451         }
    452     }
    453 
    454     /**
    455      * isShutdown is false before shutdown, true after
    456      */
    457     public void testIsShutdown() {
    458 
    459         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    460         try {
    461             assertFalse(p.isShutdown());
    462         }
    463         finally {
    464             try { p.shutdown(); } catch (SecurityException ok) { return; }
    465         }
    466         assertTrue(p.isShutdown());
    467     }
    468 
    469     /**
    470      * isTerminated is false before termination, true after
    471      */
    472     public void testIsTerminated() throws InterruptedException {
    473         final ThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    474         final CountDownLatch threadStarted = new CountDownLatch(1);
    475         final CountDownLatch done = new CountDownLatch(1);
    476         assertFalse(p.isTerminated());
    477         try {
    478             p.execute(new CheckedRunnable() {
    479                 public void realRun() throws InterruptedException {
    480                     assertFalse(p.isTerminated());
    481                     threadStarted.countDown();
    482                     done.await();
    483                 }});
    484             assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
    485             assertFalse(p.isTerminating());
    486             done.countDown();
    487         } finally {
    488             try { p.shutdown(); } catch (SecurityException ok) { return; }
    489         }
    490         assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
    491         assertTrue(p.isTerminated());
    492     }
    493 
    494     /**
    495      * isTerminating is not true when running or when terminated
    496      */
    497     public void testIsTerminating() throws InterruptedException {
    498         final ThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    499         final CountDownLatch threadStarted = new CountDownLatch(1);
    500         final CountDownLatch done = new CountDownLatch(1);
    501         try {
    502             assertFalse(p.isTerminating());
    503             p.execute(new CheckedRunnable() {
    504                 public void realRun() throws InterruptedException {
    505                     assertFalse(p.isTerminating());
    506                     threadStarted.countDown();
    507                     done.await();
    508                 }});
    509             assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
    510             assertFalse(p.isTerminating());
    511             done.countDown();
    512         } finally {
    513             try { p.shutdown(); } catch (SecurityException ok) { return; }
    514         }
    515         assertTrue(p.awaitTermination(LONG_DELAY_MS, MILLISECONDS));
    516         assertTrue(p.isTerminated());
    517         assertFalse(p.isTerminating());
    518     }
    519 
    520     /**
    521      * getQueue returns the work queue, which contains queued tasks
    522      */
    523     public void testGetQueue() throws InterruptedException {
    524         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    525         final CountDownLatch threadStarted = new CountDownLatch(1);
    526         final CountDownLatch done = new CountDownLatch(1);
    527         try {
    528             ScheduledFuture[] tasks = new ScheduledFuture[5];
    529             for (int i = 0; i < tasks.length; i++) {
    530                 Runnable r = new CheckedRunnable() {
    531                     public void realRun() throws InterruptedException {
    532                         threadStarted.countDown();
    533                         done.await();
    534                     }};
    535                 tasks[i] = p.schedule(r, 1, MILLISECONDS);
    536             }
    537             assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
    538             BlockingQueue<Runnable> q = p.getQueue();
    539             assertTrue(q.contains(tasks[tasks.length - 1]));
    540             assertFalse(q.contains(tasks[0]));
    541         } finally {
    542             done.countDown();
    543             joinPool(p);
    544         }
    545     }
    546 
    547     /**
    548      * remove(task) removes queued task, and fails to remove active task
    549      */
    550     public void testRemove() throws InterruptedException {
    551         final ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    552         ScheduledFuture[] tasks = new ScheduledFuture[5];
    553         final CountDownLatch threadStarted = new CountDownLatch(1);
    554         final CountDownLatch done = new CountDownLatch(1);
    555         try {
    556             for (int i = 0; i < tasks.length; i++) {
    557                 Runnable r = new CheckedRunnable() {
    558                     public void realRun() throws InterruptedException {
    559                         threadStarted.countDown();
    560                         done.await();
    561                     }};
    562                 tasks[i] = p.schedule(r, 1, MILLISECONDS);
    563             }
    564             assertTrue(threadStarted.await(SMALL_DELAY_MS, MILLISECONDS));
    565             BlockingQueue<Runnable> q = p.getQueue();
    566             assertFalse(p.remove((Runnable)tasks[0]));
    567             assertTrue(q.contains((Runnable)tasks[4]));
    568             assertTrue(q.contains((Runnable)tasks[3]));
    569             assertTrue(p.remove((Runnable)tasks[4]));
    570             assertFalse(p.remove((Runnable)tasks[4]));
    571             assertFalse(q.contains((Runnable)tasks[4]));
    572             assertTrue(q.contains((Runnable)tasks[3]));
    573             assertTrue(p.remove((Runnable)tasks[3]));
    574             assertFalse(q.contains((Runnable)tasks[3]));
    575         } finally {
    576             done.countDown();
    577             joinPool(p);
    578         }
    579     }
    580 
    581     /**
    582      * purge eventually removes cancelled tasks from the queue
    583      */
    584     public void testPurge() throws InterruptedException {
    585         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    586         ScheduledFuture[] tasks = new ScheduledFuture[5];
    587         for (int i = 0; i < tasks.length; i++)
    588             tasks[i] = p.schedule(new SmallPossiblyInterruptedRunnable(),
    589                                   LONG_DELAY_MS, MILLISECONDS);
    590         try {
    591             int max = tasks.length;
    592             if (tasks[4].cancel(true)) --max;
    593             if (tasks[3].cancel(true)) --max;
    594             // There must eventually be an interference-free point at
    595             // which purge will not fail. (At worst, when queue is empty.)
    596             long startTime = System.nanoTime();
    597             do {
    598                 p.purge();
    599                 long count = p.getTaskCount();
    600                 if (count == max)
    601                     return;
    602             } while (millisElapsedSince(startTime) < MEDIUM_DELAY_MS);
    603             fail("Purge failed to remove cancelled tasks");
    604         } finally {
    605             for (ScheduledFuture task : tasks)
    606                 task.cancel(true);
    607             joinPool(p);
    608         }
    609     }
    610 
    611     /**
    612      * shutdownNow returns a list containing tasks that were not run
    613      */
    614     public void testShutdownNow() {
    615         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    616         for (int i = 0; i < 5; i++)
    617             p.schedule(new SmallPossiblyInterruptedRunnable(),
    618                        LONG_DELAY_MS, MILLISECONDS);
    619         try {
    620             List<Runnable> l = p.shutdownNow();
    621             assertTrue(p.isShutdown());
    622             assertEquals(5, l.size());
    623         } catch (SecurityException ok) {
    624             // Allowed in case test doesn't have privs
    625         } finally {
    626             joinPool(p);
    627         }
    628     }
    629 
    630     /**
    631      * In default setting, shutdown cancels periodic but not delayed
    632      * tasks at shutdown
    633      */
    634     public void testShutdown1() throws InterruptedException {
    635         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    636         assertTrue(p.getExecuteExistingDelayedTasksAfterShutdownPolicy());
    637         assertFalse(p.getContinueExistingPeriodicTasksAfterShutdownPolicy());
    638 
    639         ScheduledFuture[] tasks = new ScheduledFuture[5];
    640         for (int i = 0; i < tasks.length; i++)
    641             tasks[i] = p.schedule(new NoOpRunnable(),
    642                                   SHORT_DELAY_MS, MILLISECONDS);
    643         try { p.shutdown(); } catch (SecurityException ok) { return; }
    644         BlockingQueue<Runnable> q = p.getQueue();
    645         for (ScheduledFuture task : tasks) {
    646             assertFalse(task.isDone());
    647             assertFalse(task.isCancelled());
    648             assertTrue(q.contains(task));
    649         }
    650         assertTrue(p.isShutdown());
    651         assertTrue(p.awaitTermination(SMALL_DELAY_MS, MILLISECONDS));
    652         assertTrue(p.isTerminated());
    653         for (ScheduledFuture task : tasks) {
    654             assertTrue(task.isDone());
    655             assertFalse(task.isCancelled());
    656         }
    657     }
    658 
    659     /**
    660      * If setExecuteExistingDelayedTasksAfterShutdownPolicy is false,
    661      * delayed tasks are cancelled at shutdown
    662      */
    663     public void testShutdown2() throws InterruptedException {
    664         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    665         p.setExecuteExistingDelayedTasksAfterShutdownPolicy(false);
    666         assertFalse(p.getExecuteExistingDelayedTasksAfterShutdownPolicy());
    667         assertFalse(p.getContinueExistingPeriodicTasksAfterShutdownPolicy());
    668         ScheduledFuture[] tasks = new ScheduledFuture[5];
    669         for (int i = 0; i < tasks.length; i++)
    670             tasks[i] = p.schedule(new NoOpRunnable(),
    671                                   SHORT_DELAY_MS, MILLISECONDS);
    672         BlockingQueue q = p.getQueue();
    673         assertEquals(tasks.length, q.size());
    674         try { p.shutdown(); } catch (SecurityException ok) { return; }
    675         assertTrue(p.isShutdown());
    676         assertTrue(q.isEmpty());
    677         assertTrue(p.awaitTermination(SMALL_DELAY_MS, MILLISECONDS));
    678         assertTrue(p.isTerminated());
    679         for (ScheduledFuture task : tasks) {
    680             assertTrue(task.isDone());
    681             assertTrue(task.isCancelled());
    682         }
    683     }
    684 
    685     /**
    686      * If setContinueExistingPeriodicTasksAfterShutdownPolicy is set false,
    687      * periodic tasks are cancelled at shutdown
    688      */
    689     public void testShutdown3() throws InterruptedException {
    690         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    691         assertTrue(p.getExecuteExistingDelayedTasksAfterShutdownPolicy());
    692         assertFalse(p.getContinueExistingPeriodicTasksAfterShutdownPolicy());
    693         p.setContinueExistingPeriodicTasksAfterShutdownPolicy(false);
    694         assertTrue(p.getExecuteExistingDelayedTasksAfterShutdownPolicy());
    695         assertFalse(p.getContinueExistingPeriodicTasksAfterShutdownPolicy());
    696         long initialDelay = LONG_DELAY_MS;
    697         ScheduledFuture task =
    698             p.scheduleAtFixedRate(new NoOpRunnable(), initialDelay,
    699                                   5, MILLISECONDS);
    700         try { p.shutdown(); } catch (SecurityException ok) { return; }
    701         assertTrue(p.isShutdown());
    702         assertTrue(p.getQueue().isEmpty());
    703         assertTrue(task.isDone());
    704         assertTrue(task.isCancelled());
    705         joinPool(p);
    706     }
    707 
    708     /**
    709      * if setContinueExistingPeriodicTasksAfterShutdownPolicy is true,
    710      * periodic tasks are not cancelled at shutdown
    711      */
    712     public void testShutdown4() throws InterruptedException {
    713         ScheduledThreadPoolExecutor p = new ScheduledThreadPoolExecutor(1);
    714         final CountDownLatch counter = new CountDownLatch(2);
    715         try {
    716             p.setContinueExistingPeriodicTasksAfterShutdownPolicy(true);
    717             assertTrue(p.getExecuteExistingDelayedTasksAfterShutdownPolicy());
    718             assertTrue(p.getContinueExistingPeriodicTasksAfterShutdownPolicy());
    719             final Runnable r = new CheckedRunnable() {
    720                 public void realRun() {
    721                     counter.countDown();
    722                 }};
    723             ScheduledFuture task =
    724                 p.scheduleAtFixedRate(r, 1, 1, MILLISECONDS);
    725             assertFalse(task.isDone());
    726             assertFalse(task.isCancelled());
    727             try { p.shutdown(); } catch (SecurityException ok) { return; }
    728             assertFalse(task.isCancelled());
    729             assertFalse(p.isTerminated());
    730             assertTrue(p.isShutdown());
    731             assertTrue(counter.await(SMALL_DELAY_MS, MILLISECONDS));
    732             assertFalse(task.isCancelled());
    733             assertTrue(task.cancel(false));
    734             assertTrue(task.isDone());
    735             assertTrue(task.isCancelled());
    736             assertTrue(p.awaitTermination(SMALL_DELAY_MS, MILLISECONDS));
    737             assertTrue(p.isTerminated());
    738         }
    739         finally {
    740             joinPool(p);
    741         }
    742     }
    743 
    744     /**
    745      * completed submit of callable returns result
    746      */
    747     public void testSubmitCallable() throws Exception {
    748         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    749         try {
    750             Future<String> future = e.submit(new StringTask());
    751             String result = future.get();
    752             assertSame(TEST_STRING, result);
    753         } finally {
    754             joinPool(e);
    755         }
    756     }
    757 
    758     /**
    759      * completed submit of runnable returns successfully
    760      */
    761     public void testSubmitRunnable() throws Exception {
    762         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    763         try {
    764             Future<?> future = e.submit(new NoOpRunnable());
    765             future.get();
    766             assertTrue(future.isDone());
    767         } finally {
    768             joinPool(e);
    769         }
    770     }
    771 
    772     /**
    773      * completed submit of (runnable, result) returns result
    774      */
    775     public void testSubmitRunnable2() throws Exception {
    776         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    777         try {
    778             Future<String> future = e.submit(new NoOpRunnable(), TEST_STRING);
    779             String result = future.get();
    780             assertSame(TEST_STRING, result);
    781         } finally {
    782             joinPool(e);
    783         }
    784     }
    785 
    786     /**
    787      * invokeAny(null) throws NPE
    788      */
    789     public void testInvokeAny1() throws Exception {
    790         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    791         try {
    792             e.invokeAny(null);
    793             shouldThrow();
    794         } catch (NullPointerException success) {
    795         } finally {
    796             joinPool(e);
    797         }
    798     }
    799 
    800     /**
    801      * invokeAny(empty collection) throws IAE
    802      */
    803     public void testInvokeAny2() throws Exception {
    804         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    805         try {
    806             e.invokeAny(new ArrayList<Callable<String>>());
    807             shouldThrow();
    808         } catch (IllegalArgumentException success) {
    809         } finally {
    810             joinPool(e);
    811         }
    812     }
    813 
    814     /**
    815      * invokeAny(c) throws NPE if c has null elements
    816      */
    817     public void testInvokeAny3() throws Exception {
    818         CountDownLatch latch = new CountDownLatch(1);
    819         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    820         List<Callable<String>> l = new ArrayList<Callable<String>>();
    821         l.add(latchAwaitingStringTask(latch));
    822         l.add(null);
    823         try {
    824             e.invokeAny(l);
    825             shouldThrow();
    826         } catch (NullPointerException success) {
    827         } finally {
    828             latch.countDown();
    829             joinPool(e);
    830         }
    831     }
    832 
    833     /**
    834      * invokeAny(c) throws ExecutionException if no task completes
    835      */
    836     public void testInvokeAny4() throws Exception {
    837         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    838         List<Callable<String>> l = new ArrayList<Callable<String>>();
    839         l.add(new NPETask());
    840         try {
    841             e.invokeAny(l);
    842             shouldThrow();
    843         } catch (ExecutionException success) {
    844             assertTrue(success.getCause() instanceof NullPointerException);
    845         } finally {
    846             joinPool(e);
    847         }
    848     }
    849 
    850     /**
    851      * invokeAny(c) returns result of some task
    852      */
    853     public void testInvokeAny5() throws Exception {
    854         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    855         try {
    856             List<Callable<String>> l = new ArrayList<Callable<String>>();
    857             l.add(new StringTask());
    858             l.add(new StringTask());
    859             String result = e.invokeAny(l);
    860             assertSame(TEST_STRING, result);
    861         } finally {
    862             joinPool(e);
    863         }
    864     }
    865 
    866     /**
    867      * invokeAll(null) throws NPE
    868      */
    869     public void testInvokeAll1() throws Exception {
    870         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    871         try {
    872             e.invokeAll(null);
    873             shouldThrow();
    874         } catch (NullPointerException success) {
    875         } finally {
    876             joinPool(e);
    877         }
    878     }
    879 
    880     /**
    881      * invokeAll(empty collection) returns empty collection
    882      */
    883     public void testInvokeAll2() throws Exception {
    884         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    885         try {
    886             List<Future<String>> r = e.invokeAll(new ArrayList<Callable<String>>());
    887             assertTrue(r.isEmpty());
    888         } finally {
    889             joinPool(e);
    890         }
    891     }
    892 
    893     /**
    894      * invokeAll(c) throws NPE if c has null elements
    895      */
    896     public void testInvokeAll3() throws Exception {
    897         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    898         List<Callable<String>> l = new ArrayList<Callable<String>>();
    899         l.add(new StringTask());
    900         l.add(null);
    901         try {
    902             e.invokeAll(l);
    903             shouldThrow();
    904         } catch (NullPointerException success) {
    905         } finally {
    906             joinPool(e);
    907         }
    908     }
    909 
    910     /**
    911      * get of invokeAll(c) throws exception on failed task
    912      */
    913     public void testInvokeAll4() throws Exception {
    914         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    915         List<Callable<String>> l = new ArrayList<Callable<String>>();
    916         l.add(new NPETask());
    917         List<Future<String>> futures = e.invokeAll(l);
    918         assertEquals(1, futures.size());
    919         try {
    920             futures.get(0).get();
    921             shouldThrow();
    922         } catch (ExecutionException success) {
    923             assertTrue(success.getCause() instanceof NullPointerException);
    924         } finally {
    925             joinPool(e);
    926         }
    927     }
    928 
    929     /**
    930      * invokeAll(c) returns results of all completed tasks
    931      */
    932     public void testInvokeAll5() throws Exception {
    933         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    934         try {
    935             List<Callable<String>> l = new ArrayList<Callable<String>>();
    936             l.add(new StringTask());
    937             l.add(new StringTask());
    938             List<Future<String>> futures = e.invokeAll(l);
    939             assertEquals(2, futures.size());
    940             for (Future<String> future : futures)
    941                 assertSame(TEST_STRING, future.get());
    942         } finally {
    943             joinPool(e);
    944         }
    945     }
    946 
    947     /**
    948      * timed invokeAny(null) throws NPE
    949      */
    950     public void testTimedInvokeAny1() throws Exception {
    951         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    952         try {
    953             e.invokeAny(null, MEDIUM_DELAY_MS, MILLISECONDS);
    954             shouldThrow();
    955         } catch (NullPointerException success) {
    956         } finally {
    957             joinPool(e);
    958         }
    959     }
    960 
    961     /**
    962      * timed invokeAny(,,null) throws NPE
    963      */
    964     public void testTimedInvokeAnyNullTimeUnit() throws Exception {
    965         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    966         List<Callable<String>> l = new ArrayList<Callable<String>>();
    967         l.add(new StringTask());
    968         try {
    969             e.invokeAny(l, MEDIUM_DELAY_MS, null);
    970             shouldThrow();
    971         } catch (NullPointerException success) {
    972         } finally {
    973             joinPool(e);
    974         }
    975     }
    976 
    977     /**
    978      * timed invokeAny(empty collection) throws IAE
    979      */
    980     public void testTimedInvokeAny2() throws Exception {
    981         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    982         try {
    983             e.invokeAny(new ArrayList<Callable<String>>(), MEDIUM_DELAY_MS, MILLISECONDS);
    984             shouldThrow();
    985         } catch (IllegalArgumentException success) {
    986         } finally {
    987             joinPool(e);
    988         }
    989     }
    990 
    991     /**
    992      * timed invokeAny(c) throws NPE if c has null elements
    993      */
    994     public void testTimedInvokeAny3() throws Exception {
    995         CountDownLatch latch = new CountDownLatch(1);
    996         ExecutorService e = new ScheduledThreadPoolExecutor(2);
    997         List<Callable<String>> l = new ArrayList<Callable<String>>();
    998         l.add(latchAwaitingStringTask(latch));
    999         l.add(null);
   1000         try {
   1001             e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
   1002             shouldThrow();
   1003         } catch (NullPointerException success) {
   1004         } finally {
   1005             latch.countDown();
   1006             joinPool(e);
   1007         }
   1008     }
   1009 
   1010     /**
   1011      * timed invokeAny(c) throws ExecutionException if no task completes
   1012      */
   1013     public void testTimedInvokeAny4() throws Exception {
   1014         ExecutorService e = new ScheduledThreadPoolExecutor(2);
   1015         List<Callable<String>> l = new ArrayList<Callable<String>>();
   1016         l.add(new NPETask());
   1017         try {
   1018             e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
   1019             shouldThrow();
   1020         } catch (ExecutionException success) {
   1021             assertTrue(success.getCause() instanceof NullPointerException);
   1022         } finally {
   1023             joinPool(e);
   1024         }
   1025     }
   1026 
   1027     /**
   1028      * timed invokeAny(c) returns result of some task
   1029      */
   1030     public void testTimedInvokeAny5() throws Exception {
   1031         ExecutorService e = new ScheduledThreadPoolExecutor(2);
   1032         try {
   1033             List<Callable<String>> l = new ArrayList<Callable<String>>();
   1034             l.add(new StringTask());
   1035             l.add(new StringTask());
   1036             String result = e.invokeAny(l, MEDIUM_DELAY_MS, MILLISECONDS);
   1037             assertSame(TEST_STRING, result);
   1038         } finally {
   1039             joinPool(e);
   1040         }
   1041     }
   1042 
   1043     /**
   1044      * timed invokeAll(null) throws NPE
   1045      */
   1046     public void testTimedInvokeAll1() throws Exception {
   1047         ExecutorService e = new ScheduledThreadPoolExecutor(2);
   1048         try {
   1049             e.invokeAll(null, MEDIUM_DELAY_MS, MILLISECONDS);
   1050             shouldThrow();
   1051         } catch (NullPointerException success) {
   1052         } finally {
   1053             joinPool(e);
   1054         }
   1055     }
   1056 
   1057     /**
   1058      * timed invokeAll(,,null) throws NPE
   1059      */
   1060     public void testTimedInvokeAllNullTimeUnit() throws Exception {
   1061         ExecutorService e = new ScheduledThreadPoolExecutor(2);
   1062         List<Callable<String>> l = new ArrayList<Callable<String>>();
   1063         l.add(new StringTask());
   1064         try {
   1065             e.invokeAll(l, MEDIUM_DELAY_MS, null);
   1066             shouldThrow();
   1067         } catch (NullPointerException success) {
   1068         } finally {
   1069             joinPool(e);
   1070         }
   1071     }
   1072 
   1073     /**
   1074      * timed invokeAll(empty collection) returns empty collection
   1075      */
   1076     public void testTimedInvokeAll2() throws Exception {
   1077         ExecutorService e = new ScheduledThreadPoolExecutor(2);
   1078         try {
   1079             List<Future<String>> r = e.invokeAll(new ArrayList<Callable<String>>(), MEDIUM_DELAY_MS, MILLISECONDS);
   1080             assertTrue(r.isEmpty());
   1081         } finally {
   1082             joinPool(e);
   1083         }
   1084     }
   1085 
   1086     /**
   1087      * timed invokeAll(c) throws NPE if c has null elements
   1088      */
   1089     public void testTimedInvokeAll3() throws Exception {
   1090         ExecutorService e = new ScheduledThreadPoolExecutor(2);
   1091         List<Callable<String>> l = new ArrayList<Callable<String>>();
   1092         l.add(new StringTask());
   1093         l.add(null);
   1094         try {
   1095             e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
   1096             shouldThrow();
   1097         } catch (NullPointerException success) {
   1098         } finally {
   1099             joinPool(e);
   1100         }
   1101     }
   1102 
   1103     /**
   1104      * get of element of invokeAll(c) throws exception on failed task
   1105      */
   1106     public void testTimedInvokeAll4() throws Exception {
   1107         ExecutorService e = new ScheduledThreadPoolExecutor(2);
   1108         List<Callable<String>> l = new ArrayList<Callable<String>>();
   1109         l.add(new NPETask());
   1110         List<Future<String>> futures =
   1111             e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
   1112         assertEquals(1, futures.size());
   1113         try {
   1114             futures.get(0).get();
   1115             shouldThrow();
   1116         } catch (ExecutionException success) {
   1117             assertTrue(success.getCause() instanceof NullPointerException);
   1118         } finally {
   1119             joinPool(e);
   1120         }
   1121     }
   1122 
   1123     /**
   1124      * timed invokeAll(c) returns results of all completed tasks
   1125      */
   1126     public void testTimedInvokeAll5() throws Exception {
   1127         ExecutorService e = new ScheduledThreadPoolExecutor(2);
   1128         try {
   1129             List<Callable<String>> l = new ArrayList<Callable<String>>();
   1130             l.add(new StringTask());
   1131             l.add(new StringTask());
   1132             List<Future<String>> futures =
   1133                 e.invokeAll(l, MEDIUM_DELAY_MS, MILLISECONDS);
   1134             assertEquals(2, futures.size());
   1135             for (Future<String> future : futures)
   1136                 assertSame(TEST_STRING, future.get());
   1137         } finally {
   1138             joinPool(e);
   1139         }
   1140     }
   1141 
   1142     /**
   1143      * timed invokeAll(c) cancels tasks not completed by timeout
   1144      */
   1145     public void testTimedInvokeAll6() throws Exception {
   1146         ExecutorService e = new ScheduledThreadPoolExecutor(2);
   1147         try {
   1148             List<Callable<String>> l = new ArrayList<Callable<String>>();
   1149             l.add(new StringTask());
   1150             l.add(Executors.callable(new MediumPossiblyInterruptedRunnable(), TEST_STRING));
   1151             l.add(new StringTask());
   1152             List<Future<String>> futures =
   1153                 e.invokeAll(l, SHORT_DELAY_MS, MILLISECONDS);
   1154             assertEquals(l.size(), futures.size());
   1155             for (Future future : futures)
   1156                 assertTrue(future.isDone());
   1157             assertFalse(futures.get(0).isCancelled());
   1158             assertTrue(futures.get(1).isCancelled());
   1159         } finally {
   1160             joinPool(e);
   1161         }
   1162     }
   1163 
   1164 }
   1165