18f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle/*
28f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle * Written by Doug Lea and Martin Buchholz with assistance from
38f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle * members of JCP JSR-166 Expert Group and released to the public
48f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle * domain, as explained at
58f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle * http://creativecommons.org/publicdomain/zero/1.0/
68f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle * Other contributors include Andrew Wright, Jeffrey Hayes,
78f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle * Pat Fisher, Mike Judd.
88f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle */
98f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
108f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravlepackage jsr166;
118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
128e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport static java.util.concurrent.TimeUnit.MILLISECONDS;
138e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath
148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravleimport java.util.concurrent.CountDownLatch;
158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravleimport java.util.concurrent.atomic.AtomicBoolean;
168f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravleimport java.util.concurrent.locks.LockSupport;
178e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath
188e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport junit.framework.Test;
198e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamathimport junit.framework.TestSuite;
208f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
218f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravlepublic class LockSupportTest extends JSR166TestCase {
228e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // android-note: Removed because the CTS runner does a bad job of
238e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // retrying tests that have suite() declarations.
248e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    //
258e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // public static void main(String[] args) {
268e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    //     main(suite(), args);
278e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // }
288e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // public static Test suite() {
298e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    //     return new TestSuite(...);
308e9a0e92906742b17eb08d7fb83cca91965f9b8eNarayan Kamath    // }
318f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * Returns the blocker object used by tests in this file.
348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * Any old object will do; we'll return a convenient one.
358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
368f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    static Object theBlocker() {
378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        return LockSupportTest.class;
388f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
398f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    enum ParkMethod {
418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        park() {
428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            void park() {
438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                LockSupport.park();
448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            void park(long millis) {
468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                throw new UnsupportedOperationException();
478f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
488f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        },
498f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        parkUntil() {
508f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            void park(long millis) {
518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                LockSupport.parkUntil(deadline(millis));
528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        },
548f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        parkNanos() {
558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            void park(long millis) {
568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                LockSupport.parkNanos(MILLISECONDS.toNanos(millis));
578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        },
598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        parkBlocker() {
608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            void park() {
618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                LockSupport.park(theBlocker());
628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            void park(long millis) {
648f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                throw new UnsupportedOperationException();
658f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
668f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        },
678f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        parkUntilBlocker() {
688f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            void park(long millis) {
698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                LockSupport.parkUntil(theBlocker(), deadline(millis));
708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
718f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        },
728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        parkNanosBlocker() {
738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            void park(long millis) {
748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                LockSupport.parkNanos(theBlocker(),
758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                                      MILLISECONDS.toNanos(millis));
768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        };
788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        void park() { park(2 * LONG_DELAY_MS); }
808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        abstract void park(long millis);
818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        /** Returns a deadline to use with parkUntil. */
838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        long deadline(long millis) {
848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            // beware of rounding
858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            return System.currentTimeMillis() + millis + 1;
868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * park is released by subsequent unpark
918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeUnpark_park() {
938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeUnpark(ParkMethod.park);
948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeUnpark_parkNanos() {
968f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeUnpark(ParkMethod.parkNanos);
978f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeUnpark_parkUntil() {
998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeUnpark(ParkMethod.parkUntil);
1008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeUnpark_parkBlocker() {
1028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeUnpark(ParkMethod.parkBlocker);
1038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeUnpark_parkNanosBlocker() {
1058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeUnpark(ParkMethod.parkNanosBlocker);
1068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeUnpark_parkUntilBlocker() {
1088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeUnpark(ParkMethod.parkUntilBlocker);
1098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1108f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeUnpark(final ParkMethod parkMethod) {
1118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final CountDownLatch pleaseUnpark = new CountDownLatch(1);
1128f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        Thread t = newStartedThread(new CheckedRunnable() {
1138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            public void realRun() {
1148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                pleaseUnpark.countDown();
1158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                parkMethod.park();
1168f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }});
1178f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1188f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        await(pleaseUnpark);
1198f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        LockSupport.unpark(t);
1208f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        awaitTermination(t);
1218f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1228f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1238f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
1248f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * park is released by preceding unpark
1258f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
1268f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterUnpark_park() {
1278f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterUnpark(ParkMethod.park);
1288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterUnpark_parkNanos() {
1308f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterUnpark(ParkMethod.parkNanos);
1318f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterUnpark_parkUntil() {
1338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterUnpark(ParkMethod.parkUntil);
1348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterUnpark_parkBlocker() {
1368f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterUnpark(ParkMethod.parkBlocker);
1378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1388f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterUnpark_parkNanosBlocker() {
1398f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterUnpark(ParkMethod.parkNanosBlocker);
1408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterUnpark_parkUntilBlocker() {
1428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterUnpark(ParkMethod.parkUntilBlocker);
1438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterUnpark(final ParkMethod parkMethod) {
1458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final CountDownLatch pleaseUnpark = new CountDownLatch(1);
1468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final AtomicBoolean pleasePark = new AtomicBoolean(false);
1478f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        Thread t = newStartedThread(new CheckedRunnable() {
1488f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            public void realRun() {
1498f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                pleaseUnpark.countDown();
1508f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                while (!pleasePark.get())
1518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    Thread.yield();
1528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                parkMethod.park();
1538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }});
1548f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        await(pleaseUnpark);
1568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        LockSupport.unpark(t);
1578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        pleasePark.set(true);
1588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        awaitTermination(t);
1598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
1628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * park is released by subsequent interrupt
1638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
1648f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeInterrupt_park() {
1658f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeInterrupt(ParkMethod.park);
1668f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1678f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeInterrupt_parkNanos() {
1688f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeInterrupt(ParkMethod.parkNanos);
1698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeInterrupt_parkUntil() {
1718f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeInterrupt(ParkMethod.parkUntil);
1728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeInterrupt_parkBlocker() {
1748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeInterrupt(ParkMethod.parkBlocker);
1758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeInterrupt_parkNanosBlocker() {
1778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeInterrupt(ParkMethod.parkNanosBlocker);
1788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeInterrupt_parkUntilBlocker() {
1808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkBeforeInterrupt(ParkMethod.parkUntilBlocker);
1818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkBeforeInterrupt(final ParkMethod parkMethod) {
1838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final CountDownLatch pleaseInterrupt = new CountDownLatch(1);
1848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        Thread t = newStartedThread(new CheckedRunnable() {
1858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            public void realRun() {
1868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                pleaseInterrupt.countDown();
1878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                do {
1888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    parkMethod.park();
1898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    // park may return spuriously
1908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                } while (! Thread.currentThread().isInterrupted());
1918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }});
1928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        await(pleaseInterrupt);
1948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        assertThreadStaysAlive(t);
1958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        t.interrupt();
1968f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        awaitTermination(t);
1978f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
1988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
1998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
2008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * park is released by preceding interrupt
2018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
2028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterInterrupt_park() {
2038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterInterrupt(ParkMethod.park);
2048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterInterrupt_parkNanos() {
2068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterInterrupt(ParkMethod.parkNanos);
2078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterInterrupt_parkUntil() {
2098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterInterrupt(ParkMethod.parkUntil);
2108f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterInterrupt_parkBlocker() {
2128f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterInterrupt(ParkMethod.parkBlocker);
2138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterInterrupt_parkNanosBlocker() {
2158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterInterrupt(ParkMethod.parkNanosBlocker);
2168f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2178f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterInterrupt_parkUntilBlocker() {
2188f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkAfterInterrupt(ParkMethod.parkUntilBlocker);
2198f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2208f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkAfterInterrupt(final ParkMethod parkMethod) {
2218f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final CountDownLatch pleaseInterrupt = new CountDownLatch(1);
2228f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final AtomicBoolean pleasePark = new AtomicBoolean(false);
2238f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        Thread t = newStartedThread(new CheckedRunnable() {
2248f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            public void realRun() throws Exception {
2258f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                pleaseInterrupt.countDown();
2268f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                while (!pleasePark.get())
2278f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    Thread.yield();
2288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                assertTrue(Thread.currentThread().isInterrupted());
2298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                parkMethod.park();
2308f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                assertTrue(Thread.currentThread().isInterrupted());
2318f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }});
2328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        await(pleaseInterrupt);
2348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        t.interrupt();
2358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        pleasePark.set(true);
2368f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        awaitTermination(t);
2378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2388f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2398f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
2408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed park times out if not unparked
2418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
2428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkTimesOut_parkNanos() {
2438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkTimesOut(ParkMethod.parkNanos);
2448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkTimesOut_parkUntil() {
2468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkTimesOut(ParkMethod.parkUntil);
2478f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2488f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkTimesOut_parkNanosBlocker() {
2498f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkTimesOut(ParkMethod.parkNanosBlocker);
2508f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkTimesOut_parkUntilBlocker() {
2528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkTimesOut(ParkMethod.parkUntilBlocker);
2538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2548f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkTimesOut(final ParkMethod parkMethod) {
2558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        Thread t = newStartedThread(new CheckedRunnable() {
2568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            public void realRun() {
2578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                for (;;) {
2588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    long startTime = System.nanoTime();
2598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    parkMethod.park(timeoutMillis());
2608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    // park may return spuriously
2618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    if (millisElapsedSince(startTime) >= timeoutMillis())
2628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                        return;
2638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                }
2648f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }});
2658f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2668f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        awaitTermination(t);
2678f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2688f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
2708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getBlocker(null) throws NullPointerException
2718f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
2728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetBlockerNull() {
2738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        try {
2748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            LockSupport.getBlocker(null);
2758f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            shouldThrow();
2768f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        } catch (NullPointerException success) {}
2778f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2788f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
2798f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
2808f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * getBlocker returns the blocker object passed to park
2818f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
2828f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetBlocker_parkBlocker() {
2838f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testGetBlocker(ParkMethod.parkBlocker);
2848f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2858f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetBlocker_parkNanosBlocker() {
2868f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testGetBlocker(ParkMethod.parkNanosBlocker);
2878f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2888f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetBlocker_parkUntilBlocker() {
2898f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testGetBlocker(ParkMethod.parkUntilBlocker);
2908f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
2918f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testGetBlocker(final ParkMethod parkMethod) {
2928f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        final CountDownLatch started = new CountDownLatch(1);
2938f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        Thread t = newStartedThread(new CheckedRunnable() {
2948f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            public void realRun() {
2958f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                Thread t = Thread.currentThread();
2968f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                started.countDown();
2978f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                do {
2988f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertNull(LockSupport.getBlocker(t));
2998f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    parkMethod.park();
3008f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    assertNull(LockSupport.getBlocker(t));
3018f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    // park may return spuriously
3028f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                } while (! Thread.currentThread().isInterrupted());
3038f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }});
3048f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3058f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        long startTime = System.nanoTime();
3068f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        await(started);
3078f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        for (;;) {
3088f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            Object x = LockSupport.getBlocker(t);
3098f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            if (x == theBlocker()) { // success
3108f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                t.interrupt();
3118f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                awaitTermination(t);
3128f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                assertNull(LockSupport.getBlocker(t));
3138f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                return;
3148f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            } else {
3158f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                assertNull(x);  // ok
3168f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                if (millisElapsedSince(startTime) > LONG_DELAY_MS)
3178f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                    fail("timed out");
3188f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                Thread.yield();
3198f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }
3208f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        }
3218f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3228f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3238f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
3248f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed park(0) returns immediately.
3258f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     *
3268f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * Requires hotspot fix for:
3278f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * 6763959 java.util.concurrent.locks.LockSupport.parkUntil(0) blocks forever
3288f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * which is in jdk7-b118 and 6u25.
3298f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
3308f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testPark0_parkNanos() {
3318f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testPark0(ParkMethod.parkNanos);
3328f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3338f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testPark0_parkUntil() {
3348f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testPark0(ParkMethod.parkUntil);
3358f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3368f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testPark0_parkNanosBlocker() {
3378f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testPark0(ParkMethod.parkNanosBlocker);
3388f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3398f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testPark0_parkUntilBlocker() {
3408f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testPark0(ParkMethod.parkUntilBlocker);
3418f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3428f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testPark0(final ParkMethod parkMethod) {
3438f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        Thread t = newStartedThread(new CheckedRunnable() {
3448f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            public void realRun() {
3458f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                parkMethod.park(0L);
3468f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }});
3478f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3488f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        awaitTermination(t);
3498f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3508f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3518f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    /**
3528f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     * timed park(Long.MIN_VALUE) returns immediately.
3538f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle     */
3548f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkNeg_parkNanos() {
3558f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkNeg(ParkMethod.parkNanos);
3568f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3578f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkNeg_parkUntil() {
3588f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkNeg(ParkMethod.parkUntil);
3598f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3608f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkNeg_parkNanosBlocker() {
3618f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkNeg(ParkMethod.parkNanosBlocker);
3628f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3638f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkNeg_parkUntilBlocker() {
3648f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        testParkNeg(ParkMethod.parkUntilBlocker);
3658f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3668f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    public void testParkNeg(final ParkMethod parkMethod) {
3678f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        Thread t = newStartedThread(new CheckedRunnable() {
3688f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            public void realRun() {
3698f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle                parkMethod.park(Long.MIN_VALUE);
3708f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle            }});
3718f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle
3728f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle        awaitTermination(t);
3738f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle    }
3748f0d92bba199d906c70a5e40d7f3516c1a424117Calin Juravle}
375