--- jsr166/src/test/tck/JSR166TestCase.java 2010/10/03 23:59:05 1.56 +++ jsr166/src/test/tck/JSR166TestCase.java 2011/05/09 20:00:19 1.79 @@ -1,16 +1,23 @@ /* * Written by Doug Lea with assistance from members of JCP JSR-166 * Expert Group and released to the public domain, as explained at - * http://creativecommons.org/licenses/publicdomain + * http://creativecommons.org/publicdomain/zero/1.0/ * Other contributors include Andrew Wright, Jeffrey Hayes, * Pat Fisher, Mike Judd. */ import junit.framework.*; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.ObjectInputStream; +import java.io.ObjectOutputStream; +import java.util.Arrays; +import java.util.NoSuchElementException; import java.util.PropertyPermission; import java.util.concurrent.*; import java.util.concurrent.atomic.AtomicReference; import static java.util.concurrent.TimeUnit.MILLISECONDS; +import static java.util.concurrent.TimeUnit.NANOSECONDS; import java.security.CodeSource; import java.security.Permission; import java.security.PermissionCollection; @@ -96,6 +103,42 @@ public class JSR166TestCase extends Test private static final boolean useSecurityManager = Boolean.getBoolean("jsr166.useSecurityManager"); + protected static final boolean expensiveTests = + Boolean.getBoolean("jsr166.expensiveTests"); + + /** + * If true, report on stdout all "slow" tests, that is, ones that + * take more than profileThreshold milliseconds to execute. + */ + private static final boolean profileTests = + Boolean.getBoolean("jsr166.profileTests"); + + /** + * The number of milliseconds that tests are permitted for + * execution without being reported, when profileTests is set. + */ + private static final long profileThreshold = + Long.getLong("jsr166.profileThreshold", 100); + + protected void runTest() throws Throwable { + if (profileTests) + runTestProfiled(); + else + super.runTest(); + } + + protected void runTestProfiled() throws Throwable { + long t0 = System.nanoTime(); + try { + super.runTest(); + } finally { + long elapsedMillis = + (System.nanoTime() - t0) / (1000L * 1000L); + if (elapsedMillis >= profileThreshold) + System.out.printf("%n%s: %d%n", toString(), elapsedMillis); + } + } + /** * Runs all JSR166 unit tests using junit.textui.TestRunner */ @@ -116,78 +159,88 @@ public class JSR166TestCase extends Test System.exit(0); } + public static TestSuite newTestSuite(Object... suiteOrClasses) { + TestSuite suite = new TestSuite(); + for (Object suiteOrClass : suiteOrClasses) { + if (suiteOrClass instanceof TestSuite) + suite.addTest((TestSuite) suiteOrClass); + else if (suiteOrClass instanceof Class) + suite.addTest(new TestSuite((Class) suiteOrClass)); + else + throw new ClassCastException("not a test suite or class"); + } + return suite; + } + /** - * Collects all JSR166 unit tests as one suite + * Collects all JSR166 unit tests as one suite. */ public static Test suite() { - TestSuite suite = new TestSuite("JSR166 Unit Tests"); - - suite.addTest(ForkJoinPoolTest.suite()); - suite.addTest(ForkJoinTaskTest.suite()); - suite.addTest(RecursiveActionTest.suite()); - suite.addTest(RecursiveTaskTest.suite()); - suite.addTest(LinkedTransferQueueTest.suite()); - suite.addTest(PhaserTest.suite()); - suite.addTest(ThreadLocalRandomTest.suite()); - suite.addTest(AbstractExecutorServiceTest.suite()); - suite.addTest(AbstractQueueTest.suite()); - suite.addTest(AbstractQueuedSynchronizerTest.suite()); - suite.addTest(AbstractQueuedLongSynchronizerTest.suite()); - suite.addTest(ArrayBlockingQueueTest.suite()); - suite.addTest(ArrayDequeTest.suite()); - suite.addTest(AtomicBooleanTest.suite()); - suite.addTest(AtomicIntegerArrayTest.suite()); - suite.addTest(AtomicIntegerFieldUpdaterTest.suite()); - suite.addTest(AtomicIntegerTest.suite()); - suite.addTest(AtomicLongArrayTest.suite()); - suite.addTest(AtomicLongFieldUpdaterTest.suite()); - suite.addTest(AtomicLongTest.suite()); - suite.addTest(AtomicMarkableReferenceTest.suite()); - suite.addTest(AtomicReferenceArrayTest.suite()); - suite.addTest(AtomicReferenceFieldUpdaterTest.suite()); - suite.addTest(AtomicReferenceTest.suite()); - suite.addTest(AtomicStampedReferenceTest.suite()); - suite.addTest(ConcurrentHashMapTest.suite()); - suite.addTest(ConcurrentLinkedDequeTest.suite()); - suite.addTest(ConcurrentLinkedQueueTest.suite()); - suite.addTest(ConcurrentSkipListMapTest.suite()); - suite.addTest(ConcurrentSkipListSubMapTest.suite()); - suite.addTest(ConcurrentSkipListSetTest.suite()); - suite.addTest(ConcurrentSkipListSubSetTest.suite()); - suite.addTest(CopyOnWriteArrayListTest.suite()); - suite.addTest(CopyOnWriteArraySetTest.suite()); - suite.addTest(CountDownLatchTest.suite()); - suite.addTest(CyclicBarrierTest.suite()); - suite.addTest(DelayQueueTest.suite()); - suite.addTest(EntryTest.suite()); - suite.addTest(ExchangerTest.suite()); - suite.addTest(ExecutorsTest.suite()); - suite.addTest(ExecutorCompletionServiceTest.suite()); - suite.addTest(FutureTaskTest.suite()); - suite.addTest(LinkedBlockingDequeTest.suite()); - suite.addTest(LinkedBlockingQueueTest.suite()); - suite.addTest(LinkedListTest.suite()); - suite.addTest(LockSupportTest.suite()); - suite.addTest(PriorityBlockingQueueTest.suite()); - suite.addTest(PriorityQueueTest.suite()); - suite.addTest(ReentrantLockTest.suite()); - suite.addTest(ReentrantReadWriteLockTest.suite()); - suite.addTest(ScheduledExecutorTest.suite()); - suite.addTest(ScheduledExecutorSubclassTest.suite()); - suite.addTest(SemaphoreTest.suite()); - suite.addTest(SynchronousQueueTest.suite()); - suite.addTest(SystemTest.suite()); - suite.addTest(ThreadLocalTest.suite()); - suite.addTest(ThreadPoolExecutorTest.suite()); - suite.addTest(ThreadPoolExecutorSubclassTest.suite()); - suite.addTest(ThreadTest.suite()); - suite.addTest(TimeUnitTest.suite()); - suite.addTest(TreeMapTest.suite()); - suite.addTest(TreeSetTest.suite()); - suite.addTest(TreeSubMapTest.suite()); - suite.addTest(TreeSubSetTest.suite()); - - return suite; + return newTestSuite( + ForkJoinPoolTest.suite(), + ForkJoinTaskTest.suite(), + RecursiveActionTest.suite(), + RecursiveTaskTest.suite(), + LinkedTransferQueueTest.suite(), + PhaserTest.suite(), + ThreadLocalRandomTest.suite(), + AbstractExecutorServiceTest.suite(), + AbstractQueueTest.suite(), + AbstractQueuedSynchronizerTest.suite(), + AbstractQueuedLongSynchronizerTest.suite(), + ArrayBlockingQueueTest.suite(), + ArrayDequeTest.suite(), + AtomicBooleanTest.suite(), + AtomicIntegerArrayTest.suite(), + AtomicIntegerFieldUpdaterTest.suite(), + AtomicIntegerTest.suite(), + AtomicLongArrayTest.suite(), + AtomicLongFieldUpdaterTest.suite(), + AtomicLongTest.suite(), + AtomicMarkableReferenceTest.suite(), + AtomicReferenceArrayTest.suite(), + AtomicReferenceFieldUpdaterTest.suite(), + AtomicReferenceTest.suite(), + AtomicStampedReferenceTest.suite(), + ConcurrentHashMapTest.suite(), + ConcurrentLinkedDequeTest.suite(), + ConcurrentLinkedQueueTest.suite(), + ConcurrentSkipListMapTest.suite(), + ConcurrentSkipListSubMapTest.suite(), + ConcurrentSkipListSetTest.suite(), + ConcurrentSkipListSubSetTest.suite(), + CopyOnWriteArrayListTest.suite(), + CopyOnWriteArraySetTest.suite(), + CountDownLatchTest.suite(), + CyclicBarrierTest.suite(), + DelayQueueTest.suite(), + EntryTest.suite(), + ExchangerTest.suite(), + ExecutorsTest.suite(), + ExecutorCompletionServiceTest.suite(), + FutureTaskTest.suite(), + LinkedBlockingDequeTest.suite(), + LinkedBlockingQueueTest.suite(), + LinkedListTest.suite(), + LockSupportTest.suite(), + PriorityBlockingQueueTest.suite(), + PriorityQueueTest.suite(), + ReentrantLockTest.suite(), + ReentrantReadWriteLockTest.suite(), + ScheduledExecutorTest.suite(), + ScheduledExecutorSubclassTest.suite(), + SemaphoreTest.suite(), + SynchronousQueueTest.suite(), + SystemTest.suite(), + ThreadLocalTest.suite(), + ThreadPoolExecutorTest.suite(), + ThreadPoolExecutorSubclassTest.suite(), + ThreadTest.suite(), + TimeUnitTest.suite(), + TreeMapTest.suite(), + TreeSetTest.suite(), + TreeSubMapTest.suite(), + TreeSubSetTest.suite()); } @@ -213,7 +266,7 @@ public class JSR166TestCase extends Test SHORT_DELAY_MS = getShortDelay(); SMALL_DELAY_MS = SHORT_DELAY_MS * 5; MEDIUM_DELAY_MS = SHORT_DELAY_MS * 10; - LONG_DELAY_MS = SHORT_DELAY_MS * 50; + LONG_DELAY_MS = SHORT_DELAY_MS * 200; } /** @@ -242,7 +295,7 @@ public class JSR166TestCase extends Test * earlier by threadRecordFailure. */ public void tearDown() throws Exception { - Throwable t = threadFailure.get(); + Throwable t = threadFailure.getAndSet(null); if (t != null) { if (t instanceof Error) throw (Error) t; @@ -250,20 +303,24 @@ public class JSR166TestCase extends Test throw (RuntimeException) t; else if (t instanceof Exception) throw (Exception) t; - else - throw new AssertionError(t); + else { + AssertionFailedError afe = + new AssertionFailedError(t.toString()); + afe.initCause(t); + throw afe; + } } } /** * Just like fail(reason), but additionally recording (using - * threadRecordFailure) any AssertionError thrown, so that the current - * testcase will fail. + * threadRecordFailure) any AssertionFailedError thrown, so that + * the current testcase will fail. */ public void threadFail(String reason) { try { fail(reason); - } catch (Throwable t) { + } catch (AssertionFailedError t) { threadRecordFailure(t); fail(reason); } @@ -271,13 +328,13 @@ public class JSR166TestCase extends Test /** * Just like assertTrue(b), but additionally recording (using - * threadRecordFailure) any AssertionError thrown, so that the current - * testcase will fail. + * threadRecordFailure) any AssertionFailedError thrown, so that + * the current testcase will fail. */ public void threadAssertTrue(boolean b) { try { assertTrue(b); - } catch (AssertionError t) { + } catch (AssertionFailedError t) { threadRecordFailure(t); throw t; } @@ -285,13 +342,13 @@ public class JSR166TestCase extends Test /** * Just like assertFalse(b), but additionally recording (using - * threadRecordFailure) any AssertionError thrown, so that the - * current testcase will fail. + * threadRecordFailure) any AssertionFailedError thrown, so that + * the current testcase will fail. */ public void threadAssertFalse(boolean b) { try { assertFalse(b); - } catch (AssertionError t) { + } catch (AssertionFailedError t) { threadRecordFailure(t); throw t; } @@ -299,13 +356,13 @@ public class JSR166TestCase extends Test /** * Just like assertNull(x), but additionally recording (using - * threadRecordFailure) any AssertionError thrown, so that the - * current testcase will fail. + * threadRecordFailure) any AssertionFailedError thrown, so that + * the current testcase will fail. */ public void threadAssertNull(Object x) { try { assertNull(x); - } catch (AssertionError t) { + } catch (AssertionFailedError t) { threadRecordFailure(t); throw t; } @@ -313,13 +370,13 @@ public class JSR166TestCase extends Test /** * Just like assertEquals(x, y), but additionally recording (using - * threadRecordFailure) any AssertionError thrown, so that the - * current testcase will fail. + * threadRecordFailure) any AssertionFailedError thrown, so that + * the current testcase will fail. */ public void threadAssertEquals(long x, long y) { try { assertEquals(x, y); - } catch (AssertionError t) { + } catch (AssertionFailedError t) { threadRecordFailure(t); throw t; } @@ -327,27 +384,29 @@ public class JSR166TestCase extends Test /** * Just like assertEquals(x, y), but additionally recording (using - * threadRecordFailure) any AssertionError thrown, so that the - * current testcase will fail. + * threadRecordFailure) any AssertionFailedError thrown, so that + * the current testcase will fail. */ public void threadAssertEquals(Object x, Object y) { try { assertEquals(x, y); - } catch (AssertionError t) { + } catch (AssertionFailedError t) { threadRecordFailure(t); throw t; + } catch (Throwable t) { + threadUnexpectedException(t); } } /** * Just like assertSame(x, y), but additionally recording (using - * threadRecordFailure) any AssertionError thrown, so that the - * current testcase will fail. + * threadRecordFailure) any AssertionFailedError thrown, so that + * the current testcase will fail. */ public void threadAssertSame(Object x, Object y) { try { assertSame(x, y); - } catch (AssertionError t) { + } catch (AssertionFailedError t) { threadRecordFailure(t); throw t; } @@ -368,20 +427,43 @@ public class JSR166TestCase extends Test } /** - * Calls threadFail with message "Unexpected exception" + ex. + * Records the given exception using {@link #threadRecordFailure}, + * then rethrows the exception, wrapping it in an + * AssertionFailedError if necessary. */ public void threadUnexpectedException(Throwable t) { threadRecordFailure(t); t.printStackTrace(); - // Rethrow, wrapping in an AssertionError if necessary if (t instanceof RuntimeException) throw (RuntimeException) t; else if (t instanceof Error) throw (Error) t; else { - AssertionError ae = new AssertionError("unexpected exception: " + t); + AssertionFailedError afe = + new AssertionFailedError("unexpected exception: " + t); t.initCause(t); - throw ae; + throw afe; + } + } + + /** + * Delays, via Thread.sleep for the given millisecond delay, but + * if the sleep is shorter than specified, may re-sleep or yield + * until time elapses. + */ + public static void delay(long ms) throws InterruptedException { + long startTime = System.nanoTime(); + long ns = ms * 1000 * 1000; + for (;;) { + if (ms > 0L) + Thread.sleep(ms); + else // too short to sleep + Thread.yield(); + long d = ns - (System.nanoTime() - startTime); + if (d > 0L) + ms = d / (1000 * 1000); + else + break; } } @@ -392,7 +474,7 @@ public class JSR166TestCase extends Test try { exec.shutdown(); assertTrue("ExecutorService did not terminate in a timely manner", - exec.awaitTermination(LONG_DELAY_MS, MILLISECONDS)); + exec.awaitTermination(2 * LONG_DELAY_MS, MILLISECONDS)); } catch (SecurityException ok) { // Allowed in case test doesn't have privs } catch (InterruptedException ie) { @@ -400,6 +482,20 @@ public class JSR166TestCase extends Test } } + /** + * Checks that thread does not terminate within timeoutMillis + * milliseconds (that is, Thread.join times out). + */ + public void assertThreadJoinTimesOut(Thread thread, long timeoutMillis) { + try { + long startTime = System.nanoTime(); + thread.join(timeoutMillis); + assertTrue(thread.isAlive()); + assertTrue(millisElapsedSince(startTime) >= timeoutMillis); + } catch (InterruptedException ie) { + fail("Unexpected InterruptedException"); + } + } /** * Fails with message "should throw exception". @@ -416,15 +512,6 @@ public class JSR166TestCase extends Test } /** - * Fails with message "Unexpected exception: " + ex. - */ - public void unexpectedException(Throwable ex) { - ex.printStackTrace(); - fail("Unexpected exception: " + ex); - } - - - /** * The number of elements to place in collections, arrays, etc. */ public static final int SIZE = 20; @@ -535,7 +622,22 @@ public class JSR166TestCase extends Test } /** - * Sleep until the timeout has elapsed, or interrupted. + * Sleeps until the given time has elapsed. + * Throws AssertionFailedError if interrupted. + */ + void sleep(long millis) { + try { + delay(millis); + } catch (InterruptedException ie) { + AssertionFailedError afe = + new AssertionFailedError("Unexpected InterruptedException"); + afe.initCause(ie); + throw afe; + } + } + + /** + * Sleeps until the timeout has elapsed, or interrupted. * Does NOT throw InterruptedException. */ void sleepTillInterrupted(long timeoutMillis) { @@ -545,14 +647,82 @@ public class JSR166TestCase extends Test } /** - * Returns a new started Thread running the given runnable. + * Waits up to the specified number of milliseconds for the given + * thread to enter a wait state: BLOCKED, WAITING, or TIMED_WAITING. + */ + void waitForThreadToEnterWaitState(Thread thread, long timeoutMillis) { + long timeoutNanos = timeoutMillis * 1000L * 1000L; + long t0 = System.nanoTime(); + for (;;) { + Thread.State s = thread.getState(); + if (s == Thread.State.BLOCKED || + s == Thread.State.WAITING || + s == Thread.State.TIMED_WAITING) + return; + else if (s == Thread.State.TERMINATED) + fail("Unexpected thread termination"); + else if (System.nanoTime() - t0 > timeoutNanos) { + threadAssertTrue(thread.isAlive()); + return; + } + Thread.yield(); + } + } + + /** + * Waits up to LONG_DELAY_MS for the given thread to enter a wait + * state: BLOCKED, WAITING, or TIMED_WAITING. + */ + void waitForThreadToEnterWaitState(Thread thread) { + waitForThreadToEnterWaitState(thread, LONG_DELAY_MS); + } + + /** + * Returns the number of milliseconds since time given by + * startNanoTime, which must have been previously returned from a + * call to {@link System.nanoTime()}. + */ + long millisElapsedSince(long startNanoTime) { + return NANOSECONDS.toMillis(System.nanoTime() - startNanoTime); + } + + /** + * Returns a new started daemon Thread running the given runnable. */ Thread newStartedThread(Runnable runnable) { Thread t = new Thread(runnable); + t.setDaemon(true); t.start(); return t; } + /** + * Waits for the specified time (in milliseconds) for the thread + * to terminate (using {@link Thread#join(long)}), else interrupts + * the thread (in the hope that it may terminate later) and fails. + */ + void awaitTermination(Thread t, long timeoutMillis) { + try { + t.join(timeoutMillis); + } catch (InterruptedException ie) { + threadUnexpectedException(ie); + } finally { + if (t.isAlive()) { + t.interrupt(); + fail("Test timed out"); + } + } + } + + /** + * Waits for LONG_DELAY_MS milliseconds for the thread to + * terminate (using {@link Thread#join(long)}), else interrupts + * the thread (in the hope that it may terminate later) and fails. + */ + void awaitTermination(Thread t) { + awaitTermination(t, LONG_DELAY_MS); + } + // Some convenient Runnable classes public abstract class CheckedRunnable implements Runnable { @@ -667,7 +837,7 @@ public class JSR166TestCase extends Test public Callable latchAwaitingStringTask(final CountDownLatch latch) { return new CheckedCallable() { - public String realCall() { + protected String realCall() { try { latch.await(); } catch (InterruptedException quittingTime) {} @@ -675,6 +845,21 @@ public class JSR166TestCase extends Test }}; } + public Runnable awaiter(final CountDownLatch latch) { + return new CheckedRunnable() { + public void realRun() throws InterruptedException { + await(latch); + }}; + } + + public void await(CountDownLatch latch) { + try { + assertTrue(latch.await(LONG_DELAY_MS, MILLISECONDS)); + } catch (Throwable t) { + threadUnexpectedException(t); + } + } + public static class NPETask implements Callable { public String call() { throw new NullPointerException(); } } @@ -685,59 +870,62 @@ public class JSR166TestCase extends Test public class ShortRunnable extends CheckedRunnable { protected void realRun() throws Throwable { - Thread.sleep(SHORT_DELAY_MS); + delay(SHORT_DELAY_MS); } } public class ShortInterruptedRunnable extends CheckedInterruptedRunnable { protected void realRun() throws InterruptedException { - Thread.sleep(SHORT_DELAY_MS); + delay(SHORT_DELAY_MS); } } public class SmallRunnable extends CheckedRunnable { protected void realRun() throws Throwable { - Thread.sleep(SMALL_DELAY_MS); + delay(SMALL_DELAY_MS); } } public class SmallPossiblyInterruptedRunnable extends CheckedRunnable { protected void realRun() { try { - Thread.sleep(SMALL_DELAY_MS); + delay(SMALL_DELAY_MS); } catch (InterruptedException ok) {} } } public class SmallCallable extends CheckedCallable { protected Object realCall() throws InterruptedException { - Thread.sleep(SMALL_DELAY_MS); + delay(SMALL_DELAY_MS); return Boolean.TRUE; } } - public class SmallInterruptedRunnable extends CheckedInterruptedRunnable { - protected void realRun() throws InterruptedException { - Thread.sleep(SMALL_DELAY_MS); - } - } - public class MediumRunnable extends CheckedRunnable { protected void realRun() throws Throwable { - Thread.sleep(MEDIUM_DELAY_MS); + delay(MEDIUM_DELAY_MS); } } public class MediumInterruptedRunnable extends CheckedInterruptedRunnable { protected void realRun() throws InterruptedException { - Thread.sleep(MEDIUM_DELAY_MS); + delay(MEDIUM_DELAY_MS); } } + public Runnable possiblyInterruptedRunnable(final long timeoutMillis) { + return new CheckedRunnable() { + protected void realRun() { + try { + delay(timeoutMillis); + } catch (InterruptedException ok) {} + }}; + } + public class MediumPossiblyInterruptedRunnable extends CheckedRunnable { protected void realRun() { try { - Thread.sleep(MEDIUM_DELAY_MS); + delay(MEDIUM_DELAY_MS); } catch (InterruptedException ok) {} } } @@ -745,7 +933,7 @@ public class JSR166TestCase extends Test public class LongPossiblyInterruptedRunnable extends CheckedRunnable { protected void realRun() { try { - Thread.sleep(LONG_DELAY_MS); + delay(LONG_DELAY_MS); } catch (InterruptedException ok) {} } } @@ -759,11 +947,38 @@ public class JSR166TestCase extends Test } } + public interface TrackedRunnable extends Runnable { + boolean isDone(); + } + + public static TrackedRunnable trackedRunnable(final long timeoutMillis) { + return new TrackedRunnable() { + private volatile boolean done = false; + public boolean isDone() { return done; } + public void run() { + try { + delay(timeoutMillis); + done = true; + } catch (InterruptedException ok) {} + } + }; + } + public static class TrackedShortRunnable implements Runnable { public volatile boolean done = false; public void run() { try { - Thread.sleep(SMALL_DELAY_MS); + delay(SHORT_DELAY_MS); + done = true; + } catch (InterruptedException ok) {} + } + } + + public static class TrackedSmallRunnable implements Runnable { + public volatile boolean done = false; + public void run() { + try { + delay(SMALL_DELAY_MS); done = true; } catch (InterruptedException ok) {} } @@ -773,7 +988,7 @@ public class JSR166TestCase extends Test public volatile boolean done = false; public void run() { try { - Thread.sleep(MEDIUM_DELAY_MS); + delay(MEDIUM_DELAY_MS); done = true; } catch (InterruptedException ok) {} } @@ -783,7 +998,7 @@ public class JSR166TestCase extends Test public volatile boolean done = false; public void run() { try { - Thread.sleep(LONG_DELAY_MS); + delay(LONG_DELAY_MS); done = true; } catch (InterruptedException ok) {} } @@ -800,7 +1015,7 @@ public class JSR166TestCase extends Test public volatile boolean done = false; public Object call() { try { - Thread.sleep(SMALL_DELAY_MS); + delay(SMALL_DELAY_MS); done = true; } catch (InterruptedException ok) {} return Boolean.TRUE; @@ -846,4 +1061,67 @@ public class JSR166TestCase extends Test ThreadPoolExecutor executor) {} } + /** + * A CyclicBarrier that fails with AssertionFailedErrors instead + * of throwing checked exceptions. + */ + public class CheckedBarrier extends CyclicBarrier { + public CheckedBarrier(int parties) { super(parties); } + + public int await() { + try { + return super.await(); + } catch (Exception e) { + AssertionFailedError afe = + new AssertionFailedError("Unexpected exception: " + e); + afe.initCause(e); + throw afe; + } + } + } + + public void checkEmpty(BlockingQueue q) { + try { + assertTrue(q.isEmpty()); + assertEquals(0, q.size()); + assertNull(q.peek()); + assertNull(q.poll()); + assertNull(q.poll(0, MILLISECONDS)); + assertEquals(q.toString(), "[]"); + assertTrue(Arrays.equals(q.toArray(), new Object[0])); + assertFalse(q.iterator().hasNext()); + try { + q.element(); + shouldThrow(); + } catch (NoSuchElementException success) {} + try { + q.iterator().next(); + shouldThrow(); + } catch (NoSuchElementException success) {} + try { + q.remove(); + shouldThrow(); + } catch (NoSuchElementException success) {} + } catch (InterruptedException ie) { + threadUnexpectedException(ie); + } + } + + @SuppressWarnings("unchecked") + public T serialClone(T o) { + try { + ByteArrayOutputStream bos = new ByteArrayOutputStream(); + ObjectOutputStream oos = new ObjectOutputStream(bos); + oos.writeObject(o); + oos.flush(); + oos.close(); + ByteArrayInputStream bin = + new ByteArrayInputStream(bos.toByteArray()); + ObjectInputStream ois = new ObjectInputStream(bin); + return (T) ois.readObject(); + } catch (Throwable t) { + threadUnexpectedException(t); + return null; + } + } }