ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/test/tck/FutureTaskTest.java
(Generate patch)

Comparing jsr166/src/test/tck/FutureTaskTest.java (file contents):
Revision 1.15 by jsr166, Fri Nov 20 00:58:01 2009 UTC vs.
Revision 1.23 by jsr166, Fri Jan 7 07:46:26 2011 UTC

# Line 9 | Line 9
9   import junit.framework.*;
10   import java.util.concurrent.*;
11   import static java.util.concurrent.TimeUnit.MILLISECONDS;
12 + import static java.util.concurrent.TimeUnit.SECONDS;
13   import java.util.*;
14  
15   public class FutureTaskTest extends JSR166TestCase {
16  
17      public static void main(String[] args) {
18 <        junit.textui.TestRunner.run (suite());
18 >        junit.textui.TestRunner.run(suite());
19      }
20      public static Test suite() {
21 <        return new TestSuite(FutureTaskTest.class);
21 >        return new TestSuite(FutureTaskTest.class);
22 >    }
23 >
24 >    void checkNotDone(Future<?> f) {
25 >        assertFalse(f.isDone());
26 >        assertFalse(f.isCancelled());
27 >    }
28 >
29 >    <T> void checkCompletedNormally(Future<T> f, T expected) {
30 >        assertTrue(f.isDone());
31 >        assertFalse(f.isCancelled());
32 >
33 >        try {
34 >            assertSame(expected, f.get());
35 >        } catch (Throwable fail) { threadUnexpectedException(fail); }
36 >        try {
37 >            assertSame(expected, f.get(5L, SECONDS));
38 >        } catch (Throwable fail) { threadUnexpectedException(fail); }
39 >
40 >        assertFalse(f.cancel(false));
41 >        assertFalse(f.cancel(true));
42 >    }
43 >
44 >    void checkCancelled(Future<?> f) {
45 >        assertTrue(f.isDone());
46 >        assertTrue(f.isCancelled());
47 >
48 >        try {
49 >            f.get();
50 >            shouldThrow();
51 >        } catch (CancellationException success) {
52 >        } catch (Throwable fail) { threadUnexpectedException(fail); }
53 >
54 >        try {
55 >            f.get(5L, SECONDS);
56 >            shouldThrow();
57 >        } catch (CancellationException success) {
58 >        } catch (Throwable fail) { threadUnexpectedException(fail); }
59 >
60 >        assertFalse(f.cancel(false));
61 >        assertFalse(f.cancel(true));
62 >    }
63 >
64 >    void checkCompletedAbnormally(Future<?> f, Throwable t) {
65 >        assertTrue(f.isDone());
66 >        assertFalse(f.isCancelled());
67 >
68 >        try {
69 >            f.get();
70 >            shouldThrow();
71 >        } catch (ExecutionException success) {
72 >            assertSame(t, success.getCause());
73 >        } catch (Throwable fail) { threadUnexpectedException(fail); }
74 >
75 >        try {
76 >            f.get(5L, SECONDS);
77 >            shouldThrow();
78 >        } catch (ExecutionException success) {
79 >            assertSame(t, success.getCause());
80 >        } catch (Throwable fail) { threadUnexpectedException(fail); }
81 >
82 >        assertFalse(f.cancel(false));
83 >        assertFalse(f.cancel(true));
84      }
85  
86      /**
# Line 36 | Line 99 | public class FutureTaskTest extends JSR1
99      public void testConstructor() {
100          try {
101              FutureTask task = new FutureTask(null);
102 <            shouldThrow("NullPointerException");
102 >            shouldThrow();
103          } catch (NullPointerException success) {}
104      }
105  
# Line 46 | Line 109 | public class FutureTaskTest extends JSR1
109      public void testConstructor2() {
110          try {
111              FutureTask task = new FutureTask(null, Boolean.TRUE);
112 <            shouldThrow("NullPointerException");
112 >            shouldThrow();
113          } catch (NullPointerException success) {}
114      }
115  
# Line 55 | Line 118 | public class FutureTaskTest extends JSR1
118       */
119      public void testIsDone() {
120          FutureTask task = new FutureTask(new NoOpCallable());
121 <        task.run();
122 <        assertTrue(task.isDone());
123 <        assertFalse(task.isCancelled());
121 >        task.run();
122 >        assertTrue(task.isDone());
123 >        checkCompletedNormally(task, Boolean.TRUE);
124      }
125  
126      /**
# Line 65 | Line 128 | public class FutureTaskTest extends JSR1
128       */
129      public void testRunAndReset() {
130          PublicFutureTask task = new PublicFutureTask(new NoOpCallable());
131 <        assertTrue(task.runAndReset());
132 <        assertFalse(task.isDone());
131 >        assertTrue(task.runAndReset());
132 >        checkNotDone(task);
133      }
134  
135      /**
# Line 75 | Line 138 | public class FutureTaskTest extends JSR1
138      public void testResetAfterCancel() {
139          PublicFutureTask task = new PublicFutureTask(new NoOpCallable());
140          assertTrue(task.cancel(false));
141 <        assertFalse(task.runAndReset());
142 <        assertTrue(task.isDone());
80 <        assertTrue(task.isCancelled());
141 >        assertFalse(task.runAndReset());
142 >        checkCancelled(task);
143      }
144  
145  
84
146      /**
147       * setting value causes get to return it
148       */
149      public void testSet() throws Exception {
150          PublicFutureTask task = new PublicFutureTask(new NoOpCallable());
151          task.set(one);
152 <        assertEquals(task.get(), one);
152 >        assertSame(task.get(), one);
153 >        checkCompletedNormally(task, one);
154      }
155  
156      /**
# Line 100 | Line 162 | public class FutureTaskTest extends JSR1
162          task.setException(nse);
163          try {
164              Object x = task.get();
165 <            shouldThrow("ExecutionException");
165 >            shouldThrow();
166          } catch (ExecutionException success) {
167              assertSame(success.getCause(), nse);
168 +            checkCompletedAbnormally(task, nse);
169          }
170      }
171  
172      /**
173 <     *  Cancelling before running succeeds
173 >     * Cancelling before running succeeds
174       */
175      public void testCancelBeforeRun() {
176          FutureTask task = new FutureTask(new NoOpCallable());
177          assertTrue(task.cancel(false));
178 <        task.run();
179 <        assertTrue(task.isDone());
117 <        assertTrue(task.isCancelled());
178 >        task.run();
179 >        checkCancelled(task);
180      }
181  
182      /**
# Line 123 | Line 185 | public class FutureTaskTest extends JSR1
185      public void testCancelBeforeRun2() {
186          FutureTask task = new FutureTask(new NoOpCallable());
187          assertTrue(task.cancel(true));
188 <        task.run();
189 <        assertTrue(task.isDone());
128 <        assertTrue(task.isCancelled());
188 >        task.run();
189 >        checkCancelled(task);
190      }
191  
192      /**
# Line 133 | Line 194 | public class FutureTaskTest extends JSR1
194       */
195      public void testCancelAfterRun() {
196          FutureTask task = new FutureTask(new NoOpCallable());
197 <        task.run();
197 >        task.run();
198          assertFalse(task.cancel(false));
199 <        assertTrue(task.isDone());
139 <        assertFalse(task.isCancelled());
199 >        checkCompletedNormally(task, Boolean.TRUE);
200      }
201  
202      /**
203       * cancel(true) interrupts a running task
204       */
205      public void testCancelInterrupt() throws InterruptedException {
206 <        final FutureTask task =
207 <            new FutureTask(new CheckedInterruptedCallable<Object>() {
208 <                public Object realCall() throws InterruptedException {
209 <                    Thread.sleep(SMALL_DELAY_MS);
210 <                    return Boolean.TRUE;
206 >        final CountDownLatch threadStarted = new CountDownLatch(1);
207 >        final FutureTask task =
208 >            new FutureTask(new CheckedCallable<Object>() {
209 >                public Object realCall() {
210 >                    threadStarted.countDown();
211 >                    long t0 = System.nanoTime();
212 >                    for (;;) {
213 >                        if (Thread.interrupted())
214 >                            return Boolean.TRUE;
215 >                        if (millisElapsedSince(t0) > MEDIUM_DELAY_MS)
216 >                            fail("interrupt not delivered");
217 >                        Thread.yield();
218 >                    }
219                  }});
220  
221 <        Thread t = new Thread(task);
222 <        t.start();
155 <        Thread.sleep(SHORT_DELAY_MS);
221 >        Thread t = newStartedThread(task);
222 >        threadStarted.await();
223          assertTrue(task.cancel(true));
224 <        t.join();
225 <        assertTrue(task.isDone());
226 <        assertTrue(task.isCancelled());
224 >        checkCancelled(task);
225 >        awaitTermination(t, MEDIUM_DELAY_MS);
226 >        checkCancelled(task);
227      }
228  
162
229      /**
230       * cancel(false) does not interrupt a running task
231       */
232      public void testCancelNoInterrupt() throws InterruptedException {
233 <        final FutureTask task =
234 <            new FutureTask(new CheckedCallable<Object>() {
235 <                public Object realCall() throws InterruptedException {
236 <                    Thread.sleep(MEDIUM_DELAY_MS);
233 >        final CountDownLatch threadStarted = new CountDownLatch(1);
234 >        final CountDownLatch cancelled = new CountDownLatch(1);
235 >        final FutureTask<Boolean> task =
236 >            new FutureTask<Boolean>(new CheckedCallable<Boolean>() {
237 >                public Boolean realCall() throws InterruptedException {
238 >                    threadStarted.countDown();
239 >                    cancelled.await(MEDIUM_DELAY_MS, MILLISECONDS);
240 >                    assertFalse(Thread.interrupted());
241                      return Boolean.TRUE;
242                  }});
243  
244 <        Thread t = new Thread(task);
245 <        t.start();
176 <        Thread.sleep(SHORT_DELAY_MS);
244 >        Thread t = newStartedThread(task);
245 >        threadStarted.await();
246          assertTrue(task.cancel(false));
247 <        t.join();
248 <        assertTrue(task.isDone());
249 <        assertTrue(task.isCancelled());
247 >        checkCancelled(task);
248 >        cancelled.countDown();
249 >        awaitTermination(t, MEDIUM_DELAY_MS);
250 >        checkCancelled(task);
251 >    }
252 >
253 >    /**
254 >     * run in one thread causes get in another thread to retrieve value
255 >     */
256 >    public void testGetRun() throws InterruptedException {
257 >        final CountDownLatch threadStarted = new CountDownLatch(1);
258 >
259 >        final FutureTask task =
260 >            new FutureTask(new CheckedCallable<Object>() {
261 >                public Object realCall() throws InterruptedException {
262 >                    return Boolean.TRUE;
263 >                }});
264 >
265 >        Thread t = newStartedThread(new CheckedRunnable() {
266 >            public void realRun() throws Exception {
267 >                threadStarted.countDown();
268 >                assertSame(Boolean.TRUE, task.get());
269 >            }});
270 >
271 >        threadStarted.await();
272 >        checkNotDone(task);
273 >        assertTrue(t.isAlive());
274 >        task.run();
275 >        checkCompletedNormally(task, Boolean.TRUE);
276 >        awaitTermination(t, MEDIUM_DELAY_MS);
277      }
278  
279      /**
280       * set in one thread causes get in another thread to retrieve value
281       */
282 <    public void testGet1() throws InterruptedException {
283 <        final FutureTask ft =
282 >    public void testGetSet() throws InterruptedException {
283 >        final CountDownLatch threadStarted = new CountDownLatch(1);
284 >
285 >        final PublicFutureTask task =
286 >            new PublicFutureTask(new CheckedCallable<Object>() {
287 >                public Object realCall() throws InterruptedException {
288 >                    return Boolean.TRUE;
289 >                }});
290 >
291 >        Thread t = newStartedThread(new CheckedRunnable() {
292 >            public void realRun() throws Exception {
293 >                threadStarted.countDown();
294 >                assertSame(Boolean.FALSE, task.get());
295 >            }});
296 >
297 >        threadStarted.await();
298 >        checkNotDone(task);
299 >        assertTrue(t.isAlive());
300 >        task.set(Boolean.FALSE);
301 >        checkCompletedNormally(task, Boolean.FALSE);
302 >        awaitTermination(t, MEDIUM_DELAY_MS);
303 >    }
304 >
305 >    /**
306 >     * run in one thread causes timed get in another thread to retrieve value
307 >     */
308 >    public void testTimedGetRun() throws InterruptedException {
309 >        final CountDownLatch threadStarted = new CountDownLatch(1);
310 >
311 >        final FutureTask task =
312              new FutureTask(new CheckedCallable<Object>() {
313 <                public Object realCall() throws InterruptedException {
313 >                public Object realCall() throws InterruptedException {
314                      return Boolean.TRUE;
315                  }});
316 <        Thread t = new Thread(new CheckedRunnable() {
316 >
317 >        Thread t = newStartedThread(new CheckedRunnable() {
318              public void realRun() throws Exception {
319 <                assertSame(Boolean.TRUE, ft.get());
319 >                threadStarted.countDown();
320 >                assertSame(Boolean.TRUE,
321 >                           task.get(MEDIUM_DELAY_MS, MILLISECONDS));
322              }});
323  
324 <        assertFalse(ft.isDone());
325 <        assertFalse(ft.isCancelled());
326 <        t.start();
327 <        Thread.sleep(SHORT_DELAY_MS);
328 <        ft.run();
329 <        t.join();
203 <        assertTrue(ft.isDone());
204 <        assertFalse(ft.isCancelled());
324 >        threadStarted.await();
325 >        checkNotDone(task);
326 >        assertTrue(t.isAlive());
327 >        task.run();
328 >        checkCompletedNormally(task, Boolean.TRUE);
329 >        awaitTermination(t, MEDIUM_DELAY_MS);
330      }
331  
332      /**
333       * set in one thread causes timed get in another thread to retrieve value
334       */
335 <    public void testTimedGet1() throws InterruptedException {
336 <        final FutureTask ft =
337 <            new FutureTask(new CheckedCallable<Object>() {
338 <                public Object realCall() throws InterruptedException {
335 >    public void testTimedGetSet() throws InterruptedException {
336 >        final CountDownLatch threadStarted = new CountDownLatch(1);
337 >
338 >        final PublicFutureTask task =
339 >            new PublicFutureTask(new CheckedCallable<Object>() {
340 >                public Object realCall() throws InterruptedException {
341                      return Boolean.TRUE;
342                  }});
343 <        Thread t = new Thread(new CheckedRunnable() {
343 >
344 >        Thread t = newStartedThread(new CheckedRunnable() {
345              public void realRun() throws Exception {
346 <                assertSame(Boolean.TRUE, ft.get(SMALL_DELAY_MS, MILLISECONDS));
346 >                threadStarted.countDown();
347 >                assertSame(Boolean.FALSE,
348 >                           task.get(MEDIUM_DELAY_MS, MILLISECONDS));
349              }});
350  
351 <        assertFalse(ft.isDone());
352 <        assertFalse(ft.isCancelled());
353 <        t.start();
354 <        Thread.sleep(SHORT_DELAY_MS);
355 <        ft.run();
356 <        t.join();
227 <        assertTrue(ft.isDone());
228 <        assertFalse(ft.isCancelled());
351 >        threadStarted.await();
352 >        checkNotDone(task);
353 >        assertTrue(t.isAlive());
354 >        task.set(Boolean.FALSE);
355 >        checkCompletedNormally(task, Boolean.FALSE);
356 >        awaitTermination(t, MEDIUM_DELAY_MS);
357      }
358  
359      /**
360 <     *  Cancelling a task causes timed get in another thread to throw CancellationException
360 >     * Cancelling a task causes timed get in another thread to throw
361 >     * CancellationException
362       */
363      public void testTimedGet_Cancellation() throws InterruptedException {
364 <        final FutureTask ft =
364 >        final CountDownLatch threadStarted = new CountDownLatch(2);
365 >        final FutureTask task =
366              new FutureTask(new CheckedInterruptedCallable<Object>() {
367 <                public Object realCall() throws InterruptedException {
368 <                    Thread.sleep(SMALL_DELAY_MS);
369 <                    return Boolean.TRUE;
367 >                public Object realCall() throws InterruptedException {
368 >                    threadStarted.countDown();
369 >                    Thread.sleep(LONG_DELAY_MS);
370 >                    return Boolean.TRUE;
371                  }});
372  
373          Thread t1 = new ThreadShouldThrow(CancellationException.class) {
374              public void realRun() throws Exception {
375 <                ft.get(MEDIUM_DELAY_MS, MILLISECONDS);
375 >                threadStarted.countDown();
376 >                task.get(MEDIUM_DELAY_MS, MILLISECONDS);
377              }};
378 <        Thread t2 = new Thread(ft);
378 >        Thread t2 = new Thread(task);
379          t1.start();
380          t2.start();
381 <        Thread.sleep(SHORT_DELAY_MS);
382 <        ft.cancel(true);
383 <        t1.join();
384 <        t2.join();
381 >        threadStarted.await();
382 >        task.cancel(true);
383 >        awaitTermination(t1, MEDIUM_DELAY_MS);
384 >        awaitTermination(t2, MEDIUM_DELAY_MS);
385 >        checkCancelled(task);
386      }
387  
388      /**
389 <     * Cancelling a task causes get in another thread to throw CancellationException
389 >     * Cancelling a task causes get in another thread to throw
390 >     * CancellationException
391       */
392      public void testGet_Cancellation() throws InterruptedException {
393 <        final FutureTask ft =
393 >        final CountDownLatch threadStarted = new CountDownLatch(2);
394 >        final FutureTask task =
395              new FutureTask(new CheckedInterruptedCallable<Object>() {
396 <                public Object realCall() throws InterruptedException {
397 <                    Thread.sleep(SMALL_DELAY_MS);
398 <                    return Boolean.TRUE;
396 >                public Object realCall() throws InterruptedException {
397 >                    threadStarted.countDown();
398 >                    Thread.sleep(LONG_DELAY_MS);
399 >                    return Boolean.TRUE;
400                  }});
401 +
402          Thread t1 = new ThreadShouldThrow(CancellationException.class) {
403              public void realRun() throws Exception {
404 <                ft.get();
404 >                threadStarted.countDown();
405 >                task.get();
406              }};
407 <
270 <        Thread t2 = new Thread(ft);
407 >        Thread t2 = new Thread(task);
408          t1.start();
409          t2.start();
410 <        Thread.sleep(SHORT_DELAY_MS);
411 <        ft.cancel(true);
412 <        t1.join();
413 <        t2.join();
410 >        threadStarted.await();
411 >        task.cancel(true);
412 >        awaitTermination(t1, MEDIUM_DELAY_MS);
413 >        awaitTermination(t2, MEDIUM_DELAY_MS);
414 >        checkCancelled(task);
415      }
416  
417  
# Line 281 | Line 419 | public class FutureTaskTest extends JSR1
419       * A runtime exception in task causes get to throw ExecutionException
420       */
421      public void testGet_ExecutionException() throws InterruptedException {
422 <        final FutureTask ft = new FutureTask(new Callable() {
423 <            public Object call() {
422 >        final FutureTask task = new FutureTask(new Callable() {
423 >            public Object call() {
424                  return 5/0;
425              }});
426  
427 <        ft.run();
427 >        task.run();
428          try {
429 <            ft.get();
430 <            shouldThrow("ExecutionException");
431 <        } catch (ExecutionException success) {
429 >            task.get();
430 >            shouldThrow();
431 >        } catch (ExecutionException success) {
432              assertTrue(success.getCause() instanceof ArithmeticException);
433 +            checkCompletedAbnormally(task, success.getCause());
434          }
435      }
436  
437      /**
438 <     *  A runtime exception in task causes timed get to throw ExecutionException
438 >     * A runtime exception in task causes timed get to throw ExecutionException
439       */
440      public void testTimedGet_ExecutionException2() throws Exception {
441 <        final FutureTask ft = new FutureTask(new Callable() {
442 <            public Object call() {
441 >        final FutureTask task = new FutureTask(new Callable() {
442 >            public Object call() {
443                  return 5/0;
444              }});
445  
446 <        ft.run();
447 <        try {
448 <            ft.get(SHORT_DELAY_MS, MILLISECONDS);
449 <            shouldThrow("ExecutionException");
450 <        } catch (ExecutionException success) {
446 >        task.run();
447 >        try {
448 >            task.get(SHORT_DELAY_MS, MILLISECONDS);
449 >            shouldThrow();
450 >        } catch (ExecutionException success) {
451              assertTrue(success.getCause() instanceof ArithmeticException);
452 +            checkCompletedAbnormally(task, success.getCause());
453          }
454      }
455  
# Line 318 | Line 458 | public class FutureTaskTest extends JSR1
458       * Interrupting a waiting get causes it to throw InterruptedException
459       */
460      public void testGet_InterruptedException() throws InterruptedException {
461 <        final FutureTask ft = new FutureTask(new NoOpCallable());
462 <        Thread t = new Thread(new CheckedInterruptedRunnable() {
461 >        final CountDownLatch threadStarted = new CountDownLatch(1);
462 >        final FutureTask task = new FutureTask(new NoOpCallable());
463 >        Thread t = newStartedThread(new CheckedInterruptedRunnable() {
464              public void realRun() throws Exception {
465 <                ft.get();
465 >                threadStarted.countDown();
466 >                task.get();
467              }});
468  
469 <        t.start();
328 <        Thread.sleep(SHORT_DELAY_MS);
469 >        threadStarted.await();
470          t.interrupt();
471 <        t.join();
471 >        awaitTermination(t, MEDIUM_DELAY_MS);
472 >        checkNotDone(task);
473      }
474  
475      /**
476 <     *  Interrupting a waiting timed get causes it to throw InterruptedException
476 >     * Interrupting a waiting timed get causes it to throw InterruptedException
477       */
478      public void testTimedGet_InterruptedException2() throws InterruptedException {
479 <        final FutureTask ft = new FutureTask(new NoOpCallable());
480 <        Thread t = new Thread(new CheckedInterruptedRunnable() {
479 >        final CountDownLatch threadStarted = new CountDownLatch(1);
480 >        final FutureTask task = new FutureTask(new NoOpCallable());
481 >        Thread t = newStartedThread(new CheckedInterruptedRunnable() {
482              public void realRun() throws Exception {
483 <                ft.get(LONG_DELAY_MS,MILLISECONDS);
483 >                threadStarted.countDown();
484 >                task.get(LONG_DELAY_MS, MILLISECONDS);
485              }});
486  
487 <        t.start();
344 <        Thread.sleep(SHORT_DELAY_MS);
487 >        threadStarted.await();
488          t.interrupt();
489 <        t.join();
489 >        awaitTermination(t, MEDIUM_DELAY_MS);
490 >        checkNotDone(task);
491      }
492  
493      /**
494       * A timed out timed get throws TimeoutException
495       */
496      public void testGet_TimeoutException() throws Exception {
497 <        try {
498 <            FutureTask ft = new FutureTask(new NoOpCallable());
499 <            ft.get(1,MILLISECONDS);
500 <            shouldThrow("TimeoutException");
501 <        } catch (TimeoutException success) {}
497 >        try {
498 >            FutureTask task = new FutureTask(new NoOpCallable());
499 >            task.get(1, MILLISECONDS);
500 >            shouldThrow();
501 >        } catch (TimeoutException success) {}
502      }
503  
504   }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines