[2) 트랜잭션과 Lock]5. 오라클 Lock(3)Enqueue Lock,commit

Yu River·2022년 6월 13일
0
post-thumbnail

Enqueue

1) 리소스 테이블

  • 일종의 배열(Array)이다.
  • Enqueue 리소스 구조체를 통합 관리하나 통합 관리하지 않고 버퍼 Lock이나 라이브러리 캐시 오브젝트처럼 개별 공유 리소스에서 소유자, 대기자 목록을 관리하는 경우도 있다.
  • 해싱 알고리즘을 사용하여 각 리소스를 찾는다.
  • 해시 키(Hash Key)는 리소스 식별자이며 각 해시 버킷에 연결 리스트(Linked List)로 연결된 해시 체인을 가지며, 여기에 리소스 구조체가 연결된다.

2) Enqueue 관리 방식에서의 Lock 획득 과정

Enqueue 방식으로 관리되는 특정 리소스(테이블, 트랜젝션 등)에 대한 Lock 획득 과정

[순서]

  1. 먼저 리소스 테이블에서 해당 리소스 구조체를 찾는다.
  2. 찾지 못하면 새로운 리소스 구조체를 할당받아 해시 체인 연결 리스트에 연결한다.
  3. 리소스 소유자 목록에 자신을 등록한다.
  4. 호환되지 않는 모드로 먼저 Lock을 획득한 세션이 있는 경우는 Lock 요청을 대기자 목록에 등록하고 대기(또는 작업을 포기)한다.
    • 소유자가 Exclusive 모드일 때는 한 순간에 하나의 세션만 Lock을 소유할 수 있다.
    • Shared 모드일 때는 여러 세션이 동시에 Lock 획득이 가능하다. 즉 , 동시에 소유자 목록에 등록할 수 있다.
    • 소유자 목록에 어떤 모드건 Lock이 등록된 상태에서 Exclusive Lock을 획득하려면 대기자 목록에서 대기하고, 앞의 Lock이 모두 해제되면 소유자로 등록된다.

3) Enqueue Lock 작동 메커니즘

[순서]

  1. A 세션이 Shared 모드로 Lock을 획득한다.
  2. B 세션이 Shared 모드로 Lock을 획득한다.이 때 먼저 Lock을 소유한 A 세션과 호환되므로 정상적으로 Lock을 획득할 수 있다.
  3. 현재 소유자 목록에는 두 개의 세션이 존재한다.
  4. C 세션이 Exclusive 모드로 Lock을 획득하려할 때 Shared 모드와 Exclusive 모드 간에 호환성이 없으므로 대기자 목록에 자신(C 세션)을 등록하고 대기한다.
  5. 소유자 목록에 Shared 모드로 달려 있던 A, B 두 세션이 모두 Lock을 해제하면 C 세션이 Exclusive 모드로 소유자 목록에 등록한다.
  6. A 세션이 Exclusive 모드로 다시 Lock을 획득하려고 하면, Exclusive 모드와 호환되지 않으므로 대기자 목록에 자신(A)을 등록하고 대기한다.
  7. B 세션이 다시 Shared 모드로 Lock을 획득하려고 할 때도 Exclusive 모드와 호환되지 않으므로 대기자 목록에 자신(B)을 등록하고 대기한다.
  8. ⭐️ Enqueue Lock은 순서가 보장되므로 C 세션이 Lock을 해제하면 A 세션이 가장 먼저 Exclusive 모드로 Lock을 획득한다ㅏ.

Lock을 푸는 열쇠, 커밋

1) Lock 경합

블로킹

  • Lock 경합이 발생해 특정 세션의 작업을 진행하지 못하고 멈춰 선 경우이다.
  • 커밋 또는 롤백으로 해소한다.

교착상태(Deadlock)

  • 두 세션이 각각 Lock을 설정한 리소스를 서로 액세스하려고 마주보고 진행하는 상황이다.
  • 둘 중 하나가 물러나지 않으면 영영 풀릴 수 없다.
  • 교착상태가 발생하면 이를 먼저 인지한 세션이 문장 수준 롤백을 진행한 후 에러 메시지를 던진다.
    • ORA-00006: deadlock detected while waiting for resource
    • 이 메시지를 받은 세션은 커밋 또는 롤백을 결정해야 한다.
  • Lock 경합 때문에 대기 상태에 빠질 때 3초의 타임아웃을 설정하는 이유는 "교착상태 발생 인지" 하기 위해서이다.
    • 해소후 교착상태는 해소됐지만 블로킹 상태에 놓이게 되며 이 에러에 대한 예외 처리(커밋 또는 롤백)을 하지 않으면 대기상태를 지속하게 되므로 주의해야 한다.

2) 오라클은 데이터를 읽을 때 Lock을 사용하지 않음

  • 오라클은 데이터를 읽을 때 Undo를 활용하고 Lock을 사용하지 않아 다른 DBMS에 비해 상대적으로 Lock 경합이 적게 발생한다.
  • 읽는 세션의 진행을 막는 부담이 없어 필요한 만큼 트랜잭션을 충분히 길게 가져갈 수 있다.
    • 하지만 트랜잭션이 너무 길면 롤백이 필요한 경우 너무 많은 시간이 걸리며 Undo 세그먼트가 고갈되거나 Undo 세그먼트 경합을 유발한다.
  • DML Lock 때문에 동시성이 저하되지 않도록 적절한 시점에 커밋해야하지만 너무 자주 하면 Snapshot too old(ORA-01555) 에러를 유발할 가능성 높아진다.
  • LGWR가 로그 버퍼를 비우는 동안 발생하는 log file sync 대기 이벤트 때문에 성능 저하의 우려도 생긴다.
  • 잦은 커밋 때문에 성능이 느리다면 비동기식 커밋 기능 활용을 검토해야 한다.(10gR2부터 제공)

커밋 명령 옵션

1. WAIT(Default)

  • LGWR가 로그버퍼를 파일에 기록했다는 완료 메시지를 받을 때까지 대기한다.
  • 그동안 log file sync 대기 이벤트가 발생하며 이를 '동기식 커밋'이라고도 한다.
  • 일반적인 커밋(immediate wait)에서는 트랜잭션 데이터가 데이터베이스에 안전하게 저장됨을 보장한다.

2. NOWAIT

  • LGWR의 완료 메시지를 기다리지 않고 바로 다음 트랜잭션을 진행한다.
  • log file sync 대기 이벤트가 발생하지 않는다. 이를 '비동기식 커밋'이라고도 한다.
  • 트랜잭션 커밋 직후 인스턴스에 문제가 생기거나, Redo 로그가 위치한 파일 시스템에 문제가 생겨 쓰기 작업을 진행할 수 없게 되면 커밋이 정상적으로 완료되지 못할 우려가 있다.

3. IMMEDIATE(Default)

  • 커밋 명령을 받을 때마다 LGWR가 로그 버퍼를 파일에 기록한다.

4. BATCH

  • 세션 내부에 트랜젝션 데이터를 일정량 버퍼링했다가 일괄 처리한다.
  • PGA 메모리 할당량이 늘어난다.
COMMIT WRITE IMMEDIATE WAIT ;   -- 68초
COMMIT WRITE IMMEDIATE NOWAIT ; -- 9초
COMMIT WRITE BATCH WAIT ;       -- 66초
COMMIT WRITE BATCH NOWAIT ;     -- 6초 
profile
도광양회(韜光養晦) ‘빛을 감추고 어둠속에서 힘을 기른다’

0개의 댓글