Skip to content

Instantly share code, notes, and snippets.

@kostapc
Created December 6, 2016 16:27
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save kostapc/c8009779b61cd3918a03efc5b1f81fe6 to your computer and use it in GitHub Desktop.
Save kostapc/c8009779b61cd3918a03efc5b1f81fe6 to your computer and use it in GitHub Desktop.
Single Latch - thread wait for "open" or pass through await() instantly if latch open
public class SingleLatch {
static final int STATE_OPEN = 0;
static final int STATE_CLOSED = 1;
public enum State {
OPEN(STATE_OPEN),
CLOSED(STATE_CLOSED);
int state;
State(int state) {
this.state = state;
}
int getInt() {
return state;
}
static State valueOf(int state) {
switch (state) {
case STATE_OPEN: return OPEN;
case STATE_CLOSED: return CLOSED;
default:
throw new IllegalStateException("state "+state+" not declared");
}
}
}
/**
* Synchronization control For SingleLatch.
* Uses AQS state to represent count.
*/
private static final class Sync extends AbstractQueuedSynchronizer {
private static final long serialVersionUID = 4982267854940614374L;
Sync() {
setState(State.CLOSED.getInt());
}
State getSyncState() {
return State.valueOf(getState());
}
@Override
protected int tryAcquireShared(int acquires) {
return (getState() == STATE_OPEN) ? 1 : -1;
}
@Override
protected boolean tryReleaseShared(int releases) {
setState(STATE_OPEN);
return true;
}
}
private final SingleLatch.Sync sync;
public SingleLatch() {
this.sync = new SingleLatch.Sync();
}
public void await() throws InterruptedException {
sync.acquireSharedInterruptibly(State.OPEN.getInt());
}
public boolean await(long timeout, TimeUnit unit) throws InterruptedException {
return sync.tryAcquireSharedNanos(State.OPEN.getInt(), unit.toNanos(timeout));
}
public void open() {
sync.releaseShared(State.OPEN.getInt());
}
public boolean isClosed() {
return State.CLOSED.equals(sync.getSyncState());
}
public String toString() {
return super.toString() + "[Count = " + sync.getSyncState() + "]";
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment