Table of Contents |
---|
bsr은 복제 데이타 생성을 식별하기 위해 생성 식별자bsr uses Generation Identifiers (GI, Generation Identifiers)를 사용합니다. 이것은 bsr 내부 메카니즘에서 아래와 같은 용도로 사용됩니다.
두 노드가 실제 클러스터의 멤버인지 결정할 때 (같은 클러스터 내의 노드가 아닌 우연한 연결에 대한 식별)
노드 간 백그라운드 재동기화의 방향을 결정할 때
전체 재동기화가 필요한지 혹은 부분 재동기화로 충분한지 결정할 때
스플릿 브레인(이하 SB)을 식별할 때
생성 식별자
bsr은 다음의 경우에서 새로운 데이터 생성(Data Generation)이 시작되었음을 표시합니다.
초기 전체 동기화 시
disconnected 된 리소스가 Primary 역할로 승격할 때
Primary 역할의 리소스가 disconnecting 될 때
따라서, 리소스가 Connected 연결 상태에 있고 양 노드의 디스크 상태가 UpToDate 이면 양 노드의 현재 GI는 동일하다 라고 할 수 있습니다. 반대의 경우도 마찬가지입니다.
모든 새로운 데이터 생성은 8 바이트의 UUID(universally unique identifier) 로 식별합니다. UUID의 최하위 비트는 노드의 역할을 표현하며 Primary는 1, Secondary는 0으로 설정됩니다.
GI 튜플
bsr은 로컬 리소스 메타 데이타 내에 현재와 과거의 데이터 생성(data generation) 정보를 기본적으로 4개(Tuple)로 관리합니다.
Current UUID - 로컬노드의 현재 data generation에 대한 GI(생성 식별자)입니다. 리소스가 Connected 상태이고 동기화가 된 상태라면 이 Current UUID 는 양 노드 동일합니다.
Bitmap UUID - 디스크상의 동기화 비트맵의 변화를 추적하는 UUID입니다. 디스크의 동기화 비트맵 자체를 보면, 이 식별자는 disconnected 모드 상태에서만 관련이 있습니다. 만일 리소스가 Connected 라면 이 UUID는 항상 비어(zero)있게 됩니다.
Two Historical UUIDs - 현재의 Current UUID의 이전의 상태였던 data generation 식별자들이며 2개를 기억하고 있습니다.
이 4가지 모두를 묶어서 "generation identifier tuple" 또는 짧게 "GI 튜플" 이라고 합니다.
GI 변경 과정
새로운 데이터 생성 시작
노드간 연결이 끊어 질 때 (네트워크 오류, 수동조작 포함)
연결된 상태에서 상대 노드의 디스크가 복제 데이터를 반영할 수 없는 상태 일 경우(peer-disk:Outdated)
bsr은 위 두 가지 경우에 대해 로컬 GI를 다음과 같은 방법으로 수정합니다.
...
새로운 데이터 생성을 위해 신규 UUID를 생성합니다. 이 UUID는 Primary 노드를 위한 새로운 Current UUID가 됩니다.
이전의 UUID는 이제 비트맵 변화 상황을 추적하는 generation을 의미하기 때문에, Primary 노드에 대한 새로운 Bitmap UUID가 됩니다.
Secondary 노드에서는 GI 튜플의 변화가 없습니다.
UUID는 볼륨에 쓰기 I/O 가 발생 되었을 때 신규로 생성됩니다. 따라서 GI가 생성되는 보다 더 정확한 조건은 연결이 끊어지는 등의 기존 조건에 더해 볼륨의 쓰기 I/O 발생이 요구됩니다.
재동기화 시작
재동기화가 시작될 때 GI 튜플의 변화는 없습니다.
재동기화 완료
...
재동기화가 완료되면 동기화 소스는 비트맵 uuid 를 rotate 시키고 동기화 타겟은 동기화 소스의 GI 튜플 전체 셋을 수신하여 동일하게 반영합니다.
GI 상태 식별
노드간에 연결이 맺어지면 두 노드는 현재 사용할 수 있는 GI 를 교환하고, 거기에 맞춰서 적절한 동작을 진행하는데 여기엔 몇가지 동작이 존재합니다.
...
양쪽의 Current UUID가 비어 있는 경우
양쪽 Current UUID가 비어 있는 것으로 감지하였다면, 이런 경우는 보통 새롭게 리소스를 구성하고 동기화가 시작된 적이 없는 상황입니다. 여기서는 동기화가 자동으로 진행되지 않으며 수동으로 동기화를 시작해주어야 합니다.
...
한쪽 노드의 Current UUID가 비어 있는 경우
상대 노드의 Current UUID는 비어있고 자신의 것은 그렇지 않은 것을 감지하였다면, 이런 경우는 보통 새롭게 구성된 리소스에서 전체 동기화를 바로 시도한 상태이고, 로컬노드가 동기화의 소스로 선택된 경우입니다. bsr 내부적으로는 on-disk sync bitmap의 모든 비트를 설정하는데 디바이스 전체를 out-of-sync로 간주하겠다는 의미입니다. 그리고 소스로써 동기화를 시작합니다. 반대의 경우는 (로컬 UUID가 비어있고, 상대가 비어있지 않을 때) bsr이 동일한 절차를 진행하겠지만 로컬 노드가 타겟으로 동기화 되는 것만 다릅니다.
...
양쪽의 Current UUID가 동일한 경우
자신의 Current UUID와 상대의 UUID가 비어있지 않고 동일한 것을 감지하였다면, 이런 경우는 보통 Secondary 역할 중 disconnected 모드가 되고 disconnected 중에 어떤 노드에서도 승격이 없었던 리소스에 대해서 발생하는 경우이며 동기화가 필요하지 않은 상태이며 동기화가 진행되지도 않습니다.
...
Bitmap UUID가 상대 노드의 Current UUID와 일치하는 경우
자신의 Bitmap UUID가 상대의 Current UUID와 같고 상대의 Bitmap UUID 가 비어있음을 감지하였다면, 이런 경우는 정상적인 상태이며 Secondary 역할일 때 장애 상황이 생겨서 Primary 역할로 승격시킨 경우입니다. 이것은 상대 노드는 Primary가 된 적이 없으며 그 전까지는 동일한 data generation으로 작업되었음을 의미합니다. bsr은 로컬노드를 동기화 소스로 설정하고 백그라운드 재동기화를 할 수 있도록 준비 합니다.
반대로 로컬노드가 자신의 Bitmap UUID는 비어있고 상대의 Bitmap이 자신의 Current UUID와 동일하다는 것을 인지한다면 이것도 정상적이며 로컬 노드의 실패 이후에 발생한 것입니다. bsr은 로컬노드를 동기화 타겟으로 놓고 백그라운드 재동기화를 준비합니다.
...
Current UUID가 상대 노드의 Historical UUID와 일치하는 경우
자신의 Current UUID가 상대 노드의 Historical UUID와 일치하는 것을 감지하였다면, 이는 다음과 같은 상황을 의미합니다. 2개의 데이타 셋(data sets)이 공통의 이전 세대 내용을 공유하는 동안, 상대 노드는 최신의 데이터를 가지지만 Bitmap 정보는 지난 시점의 것이기에 사용할 수 없다는 것을 의미합니다. 따라서 일반적인 동기화로는 충분하지 못할 수 있습니다. 이런 경우 bsr은 디바이스 전체를 out-of-sync 로 마킹을 하고 로컬 노드를 동기화 타겟이 되게하여 전체 백그라운드 재동기화를 시도합니다. 이와 반대로 로컬 노드의 Historical UUID 중에 상대의 Current UUID와 매칭되는 경우에는 로컬 노드를 동기화 소스가 되게하고 그 외에는 동일한 절차를 수행합니다.
...
Bitmap UUID는 일치, Current UUID는 불일치하는 경우
자신의 Current UUID와 상대의 Current UUID와는 다르고 Bitmap UUID는 일치하는 것을 감지하였다면 스플릿 브레인(Split-brain)이 발생한 것입니다. 양 노드는 disconnect 상태로 남겨지고 자동해결이 설정되어 있지 않는 한 작업자가 직접 수동으로 스플릿 브레인 상황을 해결해야 합니다.
...
Current / Bitmap UUID 모두 불일치 하는 경우
자신의 Current, Bitmap UUID가 각각의 상대 UUID와 다른 것을 감지하였다면 이전의 생성 내용과도 관련이 없는 스플릿 브레인 상황입니다. 따라서 자동복구 설정이 되어있다 하더라도 의미가 없습니다. bsr은 disconnect 되어 StandAlone 상태가 되고 작업자가 직접 스플릿 브레인 상황을 해결해야 합니다.
...
) to identify the generation of replication data. It is used in bsr internal mechanism for the following purposes.
When deciding whether two nodes are members of a same cluster (identification of accidental connections, not nodes in the same cluster)
When determining the direction of background resynchronization between nodes
When deciding whether full resynchronization is necessary or partial resynchronization
When identifying the split brain
Generation Identifiers
bsr considers that new data generation has started in the following cases and creates a new GI.
At initial full sync
When a disconnected resource is promoted to the primary role
When the primary role resource is disconnected
The time when a new GI is created is when write I/O occurs on the disk and the actual data is changed.
So, if the resource is in a Connected state and the disk status of both nodes is UpToDate, then the current GI of both nodes is the same. The opposite is also true. all new data generation is identified by an 8-byte universally unique identifier (UUID). The least significant bit of the UUID represents the role of the node, Primary is set to 1, Secondary is set to 0.
GI tuple
bsr basically manages current and past data generation information in local resource metadata as four (Tuple).
Current UUID - Generation identifier (GI) for the current data generation of the local node. If the resource is Connected and synchronized, this Current UUID is the same for both nodes.
Bitmap UUID - A UUID that tracks changes to the sync bitmap on disk. The sync bitmap identifier of the disk is only relevant in disconnected mode. If the resource is Connected, this UUID is always zero.
Two Historical UUIDs - These are the data generation identifiers that were in the previous state of the Current UUID, and remember two.
All four are collectively called "generation identifier tuple" or "GI tuple" for short.
GI change process
Start a new GI
When the connection between nodes is lost (including network error and manual operation)
In the connected state, the disk of the other node cannot reflect the replication data (peer-disk: Outdated)
bsr modifies the local GI in the following ways for the two cases mentioned above.
...
Create a new UUID to identify new data. This UUID becomes the new Current UUID for the Primary node.
The old UUID now means generation to track the bitmap change, so it will be the new Bitmap UUID for the Primary node.
In the Secondary node, there is no change in the GI tuple.
UUID is newly created when write I/O occurs to the volume. Therefore, the more accurate condition in which the GI is generated requires that the volume write I/O occurs in addition to the existing condition such as disconnection.
Begin resync
There is no change in the GI tuple when resynchronization begins.
End resync
...
When resynchronization is complete, the synchronization source rotates the bitmap uuid, and the synchronization target receives and reflects the entire set of GI tuples from the synchronization source.
GI status identification
When a connection is established between nodes, the two nodes exchange the currently available GI, and perform appropriate actions accordingly. There are several actions here.
Both node’s current UUIDs are empty
If both Current UUIDs are detected as empty, this is usually the case with new resource configuration and synchronization has never started. Synchronization does not proceed automatically here and you must start synchronization manually.the Current UUID of one node is empty
If the current UUID of the other node is empty and it detects that it is not, this is usually the case when a full synchronization was attempted immediately from the newly configured resource, and the local node was selected as the source of synchronization. bsr internally sets all used area bits of the on-disk sync bitmap, and then start syncing as source. In the opposite case (when the local UUID is empty and the opponent is not empty) bsr will go through the same procedure, but only the local node is synchronized to the target.When both node’s current UUIDs are the same
If your current UUID and your partner's UUID are not empty and are the same, this usually happens when you are disconnected in the secondary role and there is no promotion to any node during disconnected. Synchronization is not required and synchronization is not in progress.Bitmap UUID matches the current UUID of the other node
If Bitmap UUID is the same as peer's Current UUID and peer's Bitmap UUID is empty, then this is normal and a failure occurs when local are in the Secondary role and promoted to the Primary role. This means that the peer node has never been Primary and has been working with the same data generation until then. bsr sets the local node as the synchronization source and prepares it for background resynchronization. Conversely, if the local node's Bitmap UUID is empty, and the peer's Bitmap is equal to its Current UUID, this is also normal and occurred after the local node failed. bsr sets the local node as the synchronization target and prepares for background resynchronization.Current UUID matches the historical UUID of the peer node
If your Current UUID matches the Historical UUID of the other node, it means the following. While two data sets share a common previous generation content, it means that the other node has the latest data, but the Bitmap information cannot be used because it is from the past. Therefore, normal synchronization may not be enough. In this case, bsr marks the entire device out-of-sync and attempts a full background resynchronization by making the local node a synchronization target. Conversely, if there is a case in which the historical UUID of the local node matches the peer’s Current UUID, the local node becomes the synchronization source, and the same procedure is performed otherwise.Bitmap UUID matches, Current UUID does not match
If your Current UUID is different from peer's Current UUID and the Bitmap UUID matches, then a split-brain has occurred. Both nodes are left disconnected and the administrator must manually resolve the split brain situation unless auto-resolve is enabled.Neither current nor bitmap UUIDs match, but Historical UUIDs match The local node detects that its current UUID differs from the peer’s current UUID, and that the bitmap UUID’s do not match, but historical UUID match. This is split brain with unrelated ancestor generations, thus auto-recovery strategies, even if configured, are moot. BSR disconnects and waits for manual split brain resolution.
If none of the UUIDs match
Finally, if there is no match in the GI tuples of the two nodes, it disconnects with a warning that it is irrelevant data. This is a safety measure in case you are connecting between nodes that are not related at all.