1 21 22 package org.armedbear.j; 23 24 public final class ReadWriteLock 25 { 26 private int activeReaders; 27 private int activeWriters; 28 private int waitingReaders; 29 private int waitingWriters; 30 private Thread writerThread; 31 private int lockCount; 32 33 public synchronized void lockRead() throws InterruptedException 34 { 35 if (activeReaders != 0 || allowRead()) { 36 ++activeReaders; 37 return; 38 } 39 if (Thread.currentThread() == writerThread) 42 Debug.bug(); 43 ++waitingReaders; 44 while (!allowRead()) { 45 try { 46 wait(); 47 } 48 catch (InterruptedException e) { 49 --waitingReaders; throw e; 51 } 52 } 53 --waitingReaders; 54 ++activeReaders; 55 } 56 57 public synchronized void unlockRead() 58 { 59 Debug.assertTrue(activeReaders > 0); 60 --activeReaders; 61 notifyAll(); 62 } 63 64 public synchronized void lockWrite() throws InterruptedException 65 { 66 if (writerThread != null) { 67 if (Thread.currentThread() == writerThread) { 69 ++lockCount; 71 return; 72 } 73 } 74 if (allowWrite()) { 75 claimWriteLock(); 76 return; 77 } 78 ++waitingWriters; 79 while (!allowWrite()) { 80 try { 81 wait(); 82 } 83 catch (InterruptedException e) { 84 --waitingWriters; 85 throw e; 86 } 87 } 88 --waitingWriters; 89 claimWriteLock(); 90 } 91 92 public synchronized void unlockWrite() 93 { 94 Debug.assertTrue(activeWriters == 1); 95 Debug.assertTrue(lockCount > 0); 96 Debug.assertTrue(Thread.currentThread() == writerThread); 97 if (--lockCount == 0) { 98 --activeWriters; 99 writerThread = null; 100 notifyAll(); 101 } 102 } 103 104 public synchronized boolean isWriteLocked() 105 { 106 Debug.assertTrue(activeWriters == 0 || activeWriters == 1); 107 return activeWriters == 1; 108 } 109 110 private final boolean allowRead() 111 { 112 return waitingWriters == 0 && activeWriters == 0; 113 } 114 115 private final boolean allowWrite() 116 { 117 return activeReaders == 0 && activeWriters == 0; 118 } 119 120 private void claimWriteLock() 121 { 122 ++activeWriters; 123 Debug.assertTrue(writerThread == null); 124 writerThread = Thread.currentThread(); 125 Debug.assertTrue(lockCount == 0); 126 lockCount = 1; 127 } 128 } 129 | Popular Tags |