AbstractQueuedSynchronizer — FIFO 대기 큐 기반 동기화 프레임워크
AbstractQueuedSynchronizer — FIFO 대기 큐 기반 동기화 프레임워크 (AQS)
AbstractQueuedSynchronizer는 FIFO 대기 큐에 의존하는 블로킹 락과 관련 동기화 장치(세마포어, 이벤트 등)를 구현하기 위한 프레임워크를 제공해요. 이 클래스는 단일 원자 int 값을 상태로 나타내는 대부분의 동기화 장치에 유용한 기반이 되도록 설계됐어요.
본문
하위 클래스는 이 상태를 변경하는 보호된 메서드를 정의하고, 이 객체가 획득·해제되는 관점에서 그 상태가 무엇을 의미하는지 정의해야 해요. 그러면 이 클래스의 다른 메서드들이 모든 큐잉과 블로킹 메커니즘을 수행해요. 하위 클래스는 다른 상태 필드를 유지할 수 있지만, getState(), setState(int), compareAndSetState(int, int) 메서드로 조작되는 원자적 int 값만 동기화와 관련해 추적돼요.
하위 클래스는 보통 non-public 내부 헬퍼 클래스로 정의되어 그 감싸는 클래스의 동기화 속성을 구현하는 데 쓰여요. 이 클래스는 어떤 동기화 인터페이스도 구현하지 않고, 대신 acquireInterruptibly(int) 같은 메서드를 정의해서 구체적인 락과 관련 동기화 장치가 공개 메서드를 구현할 때 호출할 수 있게 해요.
이 클래스는 기본 배타(exclusive) 모드와 공유(shared) 모드를 각각 또는 둘 다 지원해요. 배타 모드로 획득되면 다른 스레드의 획득 시도는 성공할 수 없어요. 여러 스레드의 공유 모드 획득은 (반드시는 아니지만) 성공할 수 있어요. 다른 모드에서 기다리는 스레드는 같은 FIFO 큐를 공유해요. 보통 구현 하위 클래스는 이 모드 중 하나만 지원하지만, ReadWriteLock처럼 둘 다 쓰일 수 있어요.
이 클래스는 내부 큐와 조건 객체에 대한 검사(inspection)·계측(instrumentation)·모니터링 메서드를 제공해요.
사용법 (Usage)
동기화 장치의 기반으로 이 클래스를 쓰려면 상태를 검사·수정해서 다음 메서드를 오버라이드해요: tryAcquire(int), tryRelease(int), tryAcquireShared(int), tryReleaseShared(int), isHeldExclusively(). 이 메서드들은 기본적으로 UnsupportedOperationException을 던지며, 내부적으로 스레드 안전해야 하고 일반적으로 짧고 블로킹하지 않아야 해요. 이 메서드들을 정의하는 것이 이 클래스를 쓰는 유일하게 지원되는 방법이며, 다른 모든 메서드는 독립적으로 변경할 수 없으므로 final로 선언돼요.
내부 FIFO 큐를 기반으로 하지만 이 클래스는 FIFO 획득 정책을 자동으로 강제하지 않아요. 획득 시 검사가 인큐 전에 호출되므로 새로 획득하는 스레드가 다른 블로킹·큐잉된 스레드보다 앞서 나갈 수 있어요(barging). 공정 FIFO 획득 순서를 제공하려면 tryAcquire가 hasQueuedPredecessors()가 true를 반환하면 false를 반환하도록 정의하면 돼요.
기본 barging 전략이 일반적으로 처리량·확장성이 가장 높아요. 공정하거나 기아가 없다는 보장은 없지만, 먼저 큐에 있던 스레드가 나중 스레드보다 먼저 재경쟁할 수 있어요.
생성자
protected AbstractQueuedSynchronizer() — 동기화 상태가 0인 새 인스턴스를 만들어요.
상태 접근 메서드
protected final int getState() — 현재 동기화 상태 값을 반환해요. volatile 읽기 의미론을 가져요.
protected final void setState(int newState) — 동기화 상태 값을 설정해요. volatile 쓰기 의미론을 가져요.
protected final boolean compareAndSetState(int expect, int update) — 현재 상태가 예상 값과 같으면 (원자적으로) 설정해요. volatile 읽기·쓰기 의미론을 가져요.
하위 클래스가 구현하는 메서드
protected boolean tryAcquire(int arg) — 배타 모드에서 획득을 시도해요. Lock.tryLock() 구현에 쓰여요.
protected boolean tryRelease(int arg) — 배타 모드의 해제를 반영하도록 상태를 설정하려 시도해요.
protected int tryAcquireShared(int arg) — 공유 모드에서 획득을 시도해요. 실패 시 음수, 성공 시 0 또는 양수를 반환해요.
protected boolean tryReleaseShared(int arg) — 공유 모드의 해제를 반영하도록 상태를 설정하려 시도해요.
protected boolean isHeldExclusively() — 현재 스레드에 대해 동기화가 배타적으로 유지되면 true를 반환해요.
배타 모드 메서드
final void acquire(int arg) — 인터럽트를 무시하고 배타 모드로 획득해요. Lock.lock() 구현에 쓰여요.
final void acquireInterruptibly(int arg) — 인터럽트되면 중단하고 배타 모드로 획득해요. Lock.lockInterruptibly()에 쓰여요.
final boolean tryAcquireNanos(int arg, long nanosTimeout) — 시간 초과 시 실패, 인터럽트 시 중단하며 배타 모드로 획득을 시도해요. Lock.tryLock(long, TimeUnit)에 쓰여요.
final boolean release(int arg) — tryRelease가 true면 스레드를 블록 해제하며 배타 모드로 해제해요. Lock.unlock()에 쓰여요.
공유 모드 메서드
final void acquireShared(int arg) — 인터럽트를 무시하고 공유 모드로 획득해요.
final void acquireSharedInterruptibly(int arg) — 인터럽트되면 중단하며 공유 모드로 획득해요.
final boolean tryAcquireSharedNanos(int arg, long nanosTimeout) — 시간 초과 시 실패, 인터럽트 시 중단하며 공유 모드로 획득을 시도해요.
final boolean releaseShared(int arg) — 공유 모드로 해제해요.
큐 검사·계측 메서드
final boolean hasQueuedThreads() — 획득을 기다리는 스레드가 있는지 조회해요.
final boolean hasContended() — 경쟁이 있었는지 조회해요. 상수 시간에 반환돼요.
final Thread getFirstQueuedThread() — 큐의 첫 스레드를 반환하거나 비어 있으면 null을 반환해요.
final boolean isQueued(Thread thread) — 주어진 스레드가 큐에 있는지 반환해요.
final boolean hasQueuedPredecessors() — 현재 스레드보다 오래 기다린 스레드가 있는지 조회해요. 공정 동기화 장치가 barging을 피하는 데 쓰여요.
final int getQueueLength() — 획득을 기다리는 스레드 수의 추정치를 반환해요.
final Collection<Thread> getQueuedThreads() / getExclusiveQueuedThreads() / getSharedQueuedThreads() — 큐에 있는 스레드 컬렉션을 반환해요.
String toString() — 이 동기화 장치와 상태를 식별하는 문자열을 반환해요.
Condition 메서드
final boolean owns(ConditionObject condition) — 주어진 ConditionObject가 이 동기화 장치를 락으로 쓰는지 조회해요.
final boolean hasWaiters(ConditionObject condition) — 주어진 condition에서 기다리는 스레드가 있는지 조회해요.
final int getWaitQueueLength(ConditionObject condition) — 주어진 condition에서 기다리는 스레드 수의 추정치를 반환해요.
final Collection<Thread> getWaitingThreads(ConditionObject condition) — 주어진 condition에서 기다리는 스레드 컬렉션을 반환해요.
더 알아보기 (Learn more)
- AbstractQueuedLongSynchronizer 클래스 — long 상태 기반 버전
- AbstractOwnableSynchronizer 클래스 — 소유자 추적 기반 클래스
- Java 공식 API