< prev index next >

test/jdk/java/util/concurrent/locks/Lock/FlakyMutex.java

Print this page
8229442: AQS and lock classes refresh
Reviewed-by: martin


  32 import java.util.concurrent.CyclicBarrier;
  33 import java.util.concurrent.ExecutorService;
  34 import java.util.concurrent.Executors;
  35 import java.util.concurrent.TimeUnit;
  36 import java.util.concurrent.locks.AbstractQueuedLongSynchronizer;
  37 import java.util.concurrent.locks.Condition;
  38 import java.util.concurrent.locks.Lock;
  39 
  40 /**
  41  * This uses a variant of the standard Mutex demo, except with a
  42  * tryAcquire method that randomly throws various Throwable
  43  * subclasses.
  44  */
  45 @SuppressWarnings("serial")
  46 public class FlakyMutex implements Lock {
  47     static class MyError extends Error {}
  48     static class MyException extends Exception {}
  49     static class MyRuntimeException extends RuntimeException {}
  50 
  51     static void checkThrowable(Throwable t) {
  52         check((t instanceof MyError) ||
  53               (t instanceof MyException) ||
  54               (t instanceof MyRuntimeException));

  55     }
  56 
  57     static void realMain(String[] args) throws Throwable {
  58         final int nThreads = 3;



  59         final int iterations = 10_000;
  60         final CyclicBarrier startingGate = new CyclicBarrier(nThreads);
  61         final FlakyMutex mutex = new FlakyMutex();
  62         final ExecutorService es = Executors.newFixedThreadPool(nThreads);

  63         final Runnable task = () -> {
  64             try {

  65                 startingGate.await();
  66                 for (int i = 0; i < iterations; i++) {
  67                     for (;;) {
  68                         try { mutex.lock(); break; }
  69                         catch (Throwable t) { checkThrowable(t); }





  70                     }
  71 
  72                     try { check(! mutex.tryLock()); }
  73                     catch (Throwable t) { checkThrowable(t); }



  74 
  75                     try { check(! mutex.tryLock(1, TimeUnit.MICROSECONDS)); }
  76                     catch (Throwable t) { checkThrowable(t); }







  77 
  78                     mutex.unlock();
  79                 }
  80             } catch (Throwable t) { unexpected(t); }
  81         };
  82 
  83         for (int i = 0; i < nThreads; i++)
  84             es.submit(task);
  85         es.shutdown();
  86         // Let test harness handle timeout
  87         check(es.awaitTermination(Long.MAX_VALUE, TimeUnit.DAYS));
  88     }
  89 
  90     private static class FlakySync extends AbstractQueuedLongSynchronizer {
  91         private static final long serialVersionUID = -1L;
  92 
  93         public boolean isHeldExclusively() { return getState() == 1; }
  94 
  95         public boolean tryAcquire(long acquires) {
  96             // Sneak in some tests for queue state


 129     }
 130     public boolean tryLock(long timeout, TimeUnit unit) throws InterruptedException {
 131         return sync.tryAcquireNanos(1, unit.toNanos(timeout));
 132     }
 133     public void unlock() { sync.release(1); }
 134     public Condition newCondition()   { return sync.newCondition(); }
 135     public boolean isLocked()         { return sync.isHeldExclusively(); }
 136     public boolean hasQueuedThreads() { return sync.hasQueuedThreads(); }
 137 
 138     //--------------------- Infrastructure ---------------------------
 139     static volatile int passed = 0, failed = 0;
 140     static void pass() {passed++;}
 141     static void fail() {failed++; Thread.dumpStack();}
 142     static void fail(String msg) {System.out.println(msg); fail();}
 143     static void unexpected(Throwable t) {failed++; t.printStackTrace();}
 144     static void check(boolean cond) {if (cond) pass(); else fail();}
 145     static void equal(Object x, Object y) {
 146         if (x == null ? y == null : x.equals(y)) pass();
 147         else fail(x + " not equal to " + y);}
 148     public static void main(String[] args) throws Throwable {
 149         try {realMain(args);} catch (Throwable t) {unexpected(t);}




 150         System.out.printf("%nPassed = %d, failed = %d%n%n", passed, failed);
 151         if (failed > 0) throw new AssertionError("Some tests failed");}
 152     @SuppressWarnings("unchecked")
 153     static <T extends Throwable> void uncheckedThrow(Throwable t) throws T {
 154         throw (T)t; // rely on vacuous cast
 155     }
 156 }


  32 import java.util.concurrent.CyclicBarrier;
  33 import java.util.concurrent.ExecutorService;
  34 import java.util.concurrent.Executors;
  35 import java.util.concurrent.TimeUnit;
  36 import java.util.concurrent.locks.AbstractQueuedLongSynchronizer;
  37 import java.util.concurrent.locks.Condition;
  38 import java.util.concurrent.locks.Lock;
  39 
  40 /**
  41  * This uses a variant of the standard Mutex demo, except with a
  42  * tryAcquire method that randomly throws various Throwable
  43  * subclasses.
  44  */
  45 @SuppressWarnings("serial")
  46 public class FlakyMutex implements Lock {
  47     static class MyError extends Error {}
  48     static class MyException extends Exception {}
  49     static class MyRuntimeException extends RuntimeException {}
  50 
  51     static void checkThrowable(Throwable t) {
  52         if (!((t instanceof MyError) ||
  53               (t instanceof MyException) ||
  54               (t instanceof MyRuntimeException)))
  55             unexpected(t);
  56     }
  57 
  58     static void realMain(String[] args) throws Throwable {
  59         final ThreadLocalRandom rndMain = ThreadLocalRandom.current();
  60         final int nCpus = Runtime.getRuntime().availableProcessors();
  61         final int maxThreads = Math.min(4, nCpus);
  62         final int nThreads = rndMain.nextInt(1, maxThreads + 1);
  63         final int iterations = 10_000;
  64         final CyclicBarrier startingGate = new CyclicBarrier(nThreads);

  65         final ExecutorService es = Executors.newFixedThreadPool(nThreads);
  66         final FlakyMutex mutex = new FlakyMutex();
  67         final Runnable task = () -> {
  68             try {
  69                 ThreadLocalRandom rnd = ThreadLocalRandom.current();
  70                 startingGate.await();
  71                 for (int i = 0; i < iterations; i++) {
  72                     for (;;) {
  73                         try {
  74                             if (rnd.nextBoolean())
  75                                 mutex.lock();
  76                             else
  77                                 mutex.lockInterruptibly();
  78                             break;
  79                         } catch (Throwable t) { checkThrowable(t); }
  80                     }
  81 
  82                     if (rnd.nextBoolean()) {
  83                         try {
  84                             check(! mutex.tryLock());
  85                         } catch (Throwable t) { checkThrowable(t); }
  86                     }
  87 
  88                     if (rnd.nextInt(10) == 0) {
  89                         try {
  90                             check(! mutex.tryLock(1, TimeUnit.MICROSECONDS));
  91                         } catch (Throwable t) { checkThrowable(t); }
  92                     }
  93 
  94                     if (rnd.nextBoolean()) {
  95                         check(mutex.isLocked());
  96                     }
  97 
  98                     mutex.unlock();
  99                 }
 100             } catch (Throwable t) { unexpected(t); }
 101         };
 102 
 103         for (int i = 0; i < nThreads; i++)
 104             es.submit(task);
 105         es.shutdown();
 106         // Let test harness handle timeout
 107         check(es.awaitTermination(Long.MAX_VALUE, TimeUnit.DAYS));
 108     }
 109 
 110     private static class FlakySync extends AbstractQueuedLongSynchronizer {
 111         private static final long serialVersionUID = -1L;
 112 
 113         public boolean isHeldExclusively() { return getState() == 1; }
 114 
 115         public boolean tryAcquire(long acquires) {
 116             // Sneak in some tests for queue state


 149     }
 150     public boolean tryLock(long timeout, TimeUnit unit) throws InterruptedException {
 151         return sync.tryAcquireNanos(1, unit.toNanos(timeout));
 152     }
 153     public void unlock() { sync.release(1); }
 154     public Condition newCondition()   { return sync.newCondition(); }
 155     public boolean isLocked()         { return sync.isHeldExclusively(); }
 156     public boolean hasQueuedThreads() { return sync.hasQueuedThreads(); }
 157 
 158     //--------------------- Infrastructure ---------------------------
 159     static volatile int passed = 0, failed = 0;
 160     static void pass() {passed++;}
 161     static void fail() {failed++; Thread.dumpStack();}
 162     static void fail(String msg) {System.out.println(msg); fail();}
 163     static void unexpected(Throwable t) {failed++; t.printStackTrace();}
 164     static void check(boolean cond) {if (cond) pass(); else fail();}
 165     static void equal(Object x, Object y) {
 166         if (x == null ? y == null : x.equals(y)) pass();
 167         else fail(x + " not equal to " + y);}
 168     public static void main(String[] args) throws Throwable {
 169         int runsPerTest = Integer.getInteger("jsr166.runsPerTest", 1);
 170         try {
 171             for (int i = runsPerTest; i--> 0; )
 172                 realMain(args);
 173         } catch (Throwable t) { unexpected(t); }
 174         System.out.printf("%nPassed = %d, failed = %d%n%n", passed, failed);
 175         if (failed > 0) throw new AssertionError("Some tests failed");}
 176     @SuppressWarnings("unchecked")
 177     static <T extends Throwable> void uncheckedThrow(Throwable t) throws T {
 178         throw (T)t; // rely on vacuous cast
 179     }
 180 }
< prev index next >