코드 위치 : https://github.com/CUBRID/cubrid
storage/double_write_buffer.c: 306
/* DWB */
static DOUBLE_WRITE_BUFFER dwb_Global;
storage/double_write_buffer.c: 258
/* double write buffer 구조체 */
typedef struct double_write_buffer DOUBLE_WRITE_BUFFER;
struct double_write_buffer
{
bool logging_enabled;
DWB_BLOCK *blocks; /* DWB 안의 블록들 */
unsigned int num_blocks; /* 블록의 전체 개수 - 2의 거듭제곱 */
unsigned int num_pages; /* 페이지의 전체 개수 - 2의 거듭제곱 */
unsigned int num_block_pages; /* 블록당 페이지 수 - 2의 거듭제곱 */
unsigned int log2_num_block_pages; /* log2(블록당 페이지 수) */
volatile unsigned int blocks_flush_counter; /* The blocks flush counter */
volatile unsigned int next_block_to_flush; /* flush할 다음 블록 */
pthread_mutex_t mutex; /* wait queue 변경 시 사용될 lock */
DWB_WAIT_QUEUE wait_queue; /* DWB 구조체 변경 시 사용될 wait queue */
UINT64 volatile position_with_flags;
/*
* double write buffer 와 flags의 현재 위치
* flags는 각 블록의 상태(시작, 종료)를 유지하고 DWB 상태를 생성하고 DWB 상태를 수정한다.
* position_with_flags : 현재 페이지를 저장해야 할 블록과 슬롯의 index, 현재 블록 혹은 전체 DWB의 상태
*/
dwb_hashmap_type slots_hashmap; /* The slots hash */
int vdes; /* The volume file descriptor */
DWB_BLOCK *volatile file_sync_helper_block;
/* daemon이 fsync를 주기적으로 호출할 때 사용하는 단일 블록 포인터 */
// *INDENT-OFF*
double_write_buffer()
: logging_enabled(false),
blocks(NULL),
num_blocks(0),
num_pages(0),
num_block_pages(0),
log2_num_block_pages(0),
blocks_flush_counter(0),
next_block_to_flush(0),
mutex PTHREAD_MUTEX_INITIALIZER,
wait_queue DWB_WAIT_QUEUE_INITIALIZER,
position_with_flags(0),
slots_hashmap{},
vdes(NULL_VOLDES),
file_sync_helper_block(NULL)
{
}
// *INDENT-ON*
};
num_blocks
(블록의 전체 개수)와 num_pages
(페이지의 전체 개수)는 모두 2의 거듭제곱(2^n)이다.
IO_PAGESIZE = 16KB 기준
32 <= num_pages <= 2048
32 <= 2^(5~11) <= 2048
1 <= num_blocks <= 32
1 <= 2^(0~5) <= 32
num_block_pages = num_pages(2^a) / num_blocks(2^b)
따라서 num_block_pages
는 2^n
(n >= 0)이 된다.
때문에 log2_num_block_pages
는 n
(n >= 0)이 된다.
2진수에서 값이 2^n이라는 것은 하나의 비트만 SET 되어있다는 것을 의미한다.
따라서 log2_num_block_pages
만큼 비트를 미는 것으로 깔끔하게 쓰고있는 현재 블록을 얻을 수 있다.
값이 64인 변수를 예로 들면
log2 64 = 6
64 :
0100 0000
64 >> log2 64 = 0000 0001
본 시리즈의 글들은 CUBRID DB엔진 오픈 스터디를 진행하며 팀원들과 함께 공부한 내용을 정리한 것입니다.
Github 링크