Skip to content

Commit

Permalink
Reduce boilerplate code
Browse files Browse the repository at this point in the history
  • Loading branch information
lewiszlw committed Mar 1, 2024
1 parent 4289f7d commit 11c10e6
Show file tree
Hide file tree
Showing 5 changed files with 131 additions and 104 deletions.
51 changes: 50 additions & 1 deletion bustubx/src/buffer/buffer_pool.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,13 @@ use std::{collections::VecDeque, sync::Arc};
use crate::buffer::page::{Page, PageId};

use crate::buffer::PageRef;
use crate::storage::DiskManager;
use crate::catalog::SchemaRef;
use crate::storage::codec::{
BPlusTreeInternalPageCodec, BPlusTreeLeafPageCodec, BPlusTreePageCodec, TablePageCodec,
};
use crate::storage::{
BPlusTreeInternalPage, BPlusTreeLeafPage, BPlusTreePage, DiskManager, TablePage,
};
use crate::{BustubxError, BustubxResult};

use super::replacer::LRUKReplacer;
Expand Down Expand Up @@ -112,6 +118,49 @@ impl BufferPoolManager {
}
}

pub fn fetch_table_page(
&self,
page_id: PageId,
schema: SchemaRef,
) -> BustubxResult<(PageRef, TablePage)> {
let page = self.fetch_page(page_id)?;
let (table_page, _) = TablePageCodec::decode(page.read().unwrap().data(), schema.clone())?;
Ok((page, table_page))
}

pub fn fetch_tree_page(
&self,
page_id: PageId,
key_schema: SchemaRef,
) -> BustubxResult<(PageRef, BPlusTreePage)> {
let page = self.fetch_page(page_id)?;
let (tree_page, _) =
BPlusTreePageCodec::decode(page.read().unwrap().data(), key_schema.clone())?;
Ok((page, tree_page))
}

pub fn fetch_tree_internal_page(

Check warning on line 142 in bustubx/src/buffer/buffer_pool.rs

View workflow job for this annotation

GitHub Actions / Test Suite

methods `fetch_tree_internal_page` and `delete_page` are never used
&self,
page_id: PageId,
key_schema: SchemaRef,
) -> BustubxResult<(PageRef, BPlusTreeInternalPage)> {
let page = self.fetch_page(page_id)?;
let (tree_internal_page, _) =
BPlusTreeInternalPageCodec::decode(page.read().unwrap().data(), key_schema.clone())?;
Ok((page, tree_internal_page))
}

pub fn fetch_tree_leaf_page(
&self,
page_id: PageId,
key_schema: SchemaRef,
) -> BustubxResult<(PageRef, BPlusTreeLeafPage)> {
let page = self.fetch_page(page_id)?;
let (tree_leaf_page, _) =
BPlusTreeLeafPageCodec::decode(page.read().unwrap().data(), key_schema.clone())?;
Ok((page, tree_leaf_page))
}

// 将缓冲池中指定页写回磁盘
pub fn flush_page(&self, page_id: PageId) -> BustubxResult<bool> {
if let Some(frame_id) = self.page_table.get(&page_id) {
Expand Down
5 changes: 3 additions & 2 deletions bustubx/src/catalog/information.rs
Original file line number Diff line number Diff line change
Expand Up @@ -291,8 +291,9 @@ fn load_table_last_page_id(
) -> BustubxResult<PageId> {
let mut page_id = first_page_id;
loop {
let page = catalog.buffer_pool.fetch_page(page_id)?;
let (table_page, _) = TablePageCodec::decode(page.read().unwrap().data(), schema.clone())?;
let (_, table_page) = catalog
.buffer_pool
.fetch_table_page(page_id, schema.clone())?;

if table_page.header.next_page_id == INVALID_PAGE_ID {
return Ok(page_id);
Expand Down
6 changes: 3 additions & 3 deletions bustubx/src/common/util.rs
Original file line number Diff line number Diff line change
Expand Up @@ -98,9 +98,9 @@ pub(crate) fn pretty_format_index_tree(index: &BPlusTreeIndex) -> BustubxResult<
let mut level_row = vec![];

while let Some(page_id) = curr_queue.pop_front() {
let page = index.buffer_pool.fetch_page(page_id)?;
let (curr_page, _) =
BPlusTreePageCodec::decode(page.read().unwrap().data(), index.key_schema.clone())?;
let (_, curr_page) = index
.buffer_pool
.fetch_tree_page(page_id, index.key_schema.clone())?;

match curr_page {
BPlusTreePage::Internal(internal_page) => {
Expand Down
131 changes: 55 additions & 76 deletions bustubx/src/storage/index.rs
Original file line number Diff line number Diff line change
Expand Up @@ -100,11 +100,9 @@ impl BPlusTreeIndex {
let curr_page_id = curr_page.read().unwrap().page_id;
if let Some(parent_page_id) = context.read_set.pop_back() {
// 更新父节点
let parent_page = self.buffer_pool.fetch_page(parent_page_id)?;
let (mut parent_tree_page, _) = BPlusTreePageCodec::decode(
parent_page.read().unwrap().data(),
self.key_schema.clone(),
)?;
let (parent_page, mut parent_tree_page) = self
.buffer_pool
.fetch_tree_page(parent_page_id, self.key_schema.clone())?;
parent_tree_page.insert_internalkv(internalkv);

curr_page = parent_page;
Expand Down Expand Up @@ -205,11 +203,9 @@ impl BPlusTreeIndex {
"Cannot process index page borrow or merge".to_string(),
));
};
let new_parent_page = self.buffer_pool.fetch_page(new_parent_page_id)?;
let (new_parent_tree_page, _) = BPlusTreePageCodec::decode(
new_parent_page.read().unwrap().data(),
self.key_schema.clone(),
)?;
let (_, new_parent_tree_page) = self
.buffer_pool
.fetch_tree_page(new_parent_page_id, self.key_schema.clone())?;

curr_page_id = new_parent_page_id;
curr_tree_page = new_parent_tree_page;
Expand Down Expand Up @@ -261,11 +257,10 @@ impl BPlusTreeIndex {
if self.is_empty() {
return Ok(None);
}
let mut curr_page = self
.buffer_pool
.fetch_page(self.root_page_id.load(Ordering::SeqCst))?;
let (mut curr_tree_page, _) =
BPlusTreePageCodec::decode(curr_page.read().unwrap().data(), self.key_schema.clone())?;
let (mut curr_page, mut curr_tree_page) = self.buffer_pool.fetch_tree_page(
self.root_page_id.load(Ordering::SeqCst),
self.key_schema.clone(),
)?;

// 找到leaf page
loop {
Expand All @@ -276,11 +271,9 @@ impl BPlusTreeIndex {
.push_back(curr_page.read().unwrap().page_id);
// 查找下一页
let next_page_id = internal_page.look_up(key);
let next_page = self.buffer_pool.fetch_page(next_page_id)?;
let (next_tree_page, _) = BPlusTreePageCodec::decode(
next_page.read().unwrap().data(),
self.key_schema.clone(),
)?;
let (next_page, next_tree_page) = self
.buffer_pool
.fetch_tree_page(next_page_id, self.key_schema.clone())?;
curr_page = next_page;
curr_tree_page = next_tree_page;
}
Expand Down Expand Up @@ -357,18 +350,16 @@ impl BPlusTreeIndex {
borrowed_page_id: PageId,
min_max: bool,
) -> BustubxResult<bool> {
let borrowed_page = self.buffer_pool.fetch_page(borrowed_page_id)?;
let (mut borrowed_tree_page, _) = BPlusTreePageCodec::decode(
borrowed_page.read().unwrap().data(),
self.key_schema.clone(),
)?;
let (borrowed_page, mut borrowed_tree_page) = self
.buffer_pool
.fetch_tree_page(borrowed_page_id, self.key_schema.clone())?;
if !borrowed_tree_page.can_borrow() {
return Ok(false);
}

let page = self.buffer_pool.fetch_page(page_id)?;
let (mut tree_page, _) =
BPlusTreePageCodec::decode(page.read().unwrap().data(), self.key_schema.clone())?;
let (page, mut tree_page) = self
.buffer_pool
.fetch_tree_page(page_id, self.key_schema.clone())?;

let (old_internal_key, new_internal_key) = match borrowed_tree_page {
BPlusTreePage::Internal(ref mut borrowed_internal_page) => {
Expand Down Expand Up @@ -430,11 +421,9 @@ impl BPlusTreeIndex {
)));

// 更新父节点
let parent_page = self.buffer_pool.fetch_page(parent_page_id)?;
let (mut parent_internal_page, _) = BPlusTreeInternalPageCodec::decode(
parent_page.read().unwrap().data(),
self.key_schema.clone(),
)?;
let (parent_page, mut parent_internal_page) = self
.buffer_pool
.fetch_tree_internal_page(parent_page_id, self.key_schema.clone())?;
parent_internal_page.replace_key(&old_internal_key, new_internal_key);

parent_page.write().unwrap().set_data(page_bytes_to_array(
Expand All @@ -448,12 +437,10 @@ impl BPlusTreeIndex {
parent_page_id: PageId,
child_page_id: PageId,
) -> BustubxResult<(Option<PageId>, Option<PageId>)> {
let parent_page = self.buffer_pool.fetch_page(parent_page_id)?;
let (parent_page, _) = BPlusTreeInternalPageCodec::decode(
parent_page.read().unwrap().data(),
self.key_schema.clone(),
)?;
Ok(parent_page.sibling_page_ids(child_page_id))
let (_, parent_internal_page) = self
.buffer_pool
.fetch_tree_internal_page(parent_page_id, self.key_schema.clone())?;
Ok(parent_internal_page.sibling_page_ids(child_page_id))
}

fn merge(
Expand All @@ -462,12 +449,12 @@ impl BPlusTreeIndex {
left_page_id: PageId,
right_page_id: PageId,
) -> BustubxResult<PageId> {
let left_page = self.buffer_pool.fetch_page(left_page_id)?;
let (mut left_tree_page, _) =
BPlusTreePageCodec::decode(left_page.read().unwrap().data(), self.key_schema.clone())?;
let right_page = self.buffer_pool.fetch_page(right_page_id)?;
let (mut right_tree_page, _) =
BPlusTreePageCodec::decode(right_page.read().unwrap().data(), self.key_schema.clone())?;
let (left_page, mut left_tree_page) = self
.buffer_pool
.fetch_tree_page(left_page_id, self.key_schema.clone())?;
let (_, mut right_tree_page) = self
.buffer_pool
.fetch_tree_page(right_page_id, self.key_schema.clone())?;

// 向左合入
match left_tree_page {
Expand Down Expand Up @@ -509,11 +496,9 @@ impl BPlusTreeIndex {
self.buffer_pool.delete_page(right_page_id)?;

// 更新父节点
let parent_page = self.buffer_pool.fetch_page(parent_page_id)?;
let (mut parent_internal_page, _) = BPlusTreeInternalPageCodec::decode(
parent_page.read().unwrap().data(),
self.key_schema.clone(),
)?;
let (parent_page, mut parent_internal_page) = self
.buffer_pool
.fetch_tree_internal_page(parent_page_id, self.key_schema.clone())?;
parent_internal_page.delete_page_id(right_page_id);

// 根节点只有一个子节点(叶子)时,则叶子节点成为新的根节点
Expand Down Expand Up @@ -543,9 +528,9 @@ impl BPlusTreeIndex {
}

fn find_subtree_leafkv(&self, page_id: PageId, min_or_max: bool) -> BustubxResult<LeafKV> {
let curr_page = self.buffer_pool.fetch_page(page_id)?;
let (mut curr_tree_page, _) =
BPlusTreePageCodec::decode(curr_page.read().unwrap().data(), self.key_schema.clone())?;
let (_, mut curr_tree_page) = self
.buffer_pool
.fetch_tree_page(page_id, self.key_schema.clone())?;
loop {
match curr_tree_page {
BPlusTreePage::Internal(internal_page) => {
Expand All @@ -555,12 +540,10 @@ impl BPlusTreeIndex {
internal_page.header.current_size as usize - 1
};
let next_page_id = internal_page.value_at(index);
let next_page = self.buffer_pool.fetch_page(next_page_id)?;
curr_tree_page = BPlusTreePageCodec::decode(
next_page.read().unwrap().data(),
self.key_schema.clone(),
)?
.0;
let (_, next_tree_page) = self
.buffer_pool
.fetch_tree_page(next_page_id, self.key_schema.clone())?;
curr_tree_page = next_tree_page;
}
BPlusTreePage::Leaf(leaf_page) => {
let index = if min_or_max {
Expand All @@ -575,21 +558,18 @@ impl BPlusTreeIndex {
}

pub fn get_first_leaf_page(&self) -> BustubxResult<BPlusTreeLeafPage> {
let curr_page = self
.buffer_pool
.fetch_page(self.root_page_id.load(Ordering::SeqCst))?;
let (mut curr_tree_page, _) =
BPlusTreePageCodec::decode(curr_page.read().unwrap().data(), self.key_schema.clone())?;
let (_, mut curr_tree_page) = self.buffer_pool.fetch_tree_page(
self.root_page_id.load(Ordering::SeqCst),
self.key_schema.clone(),
)?;
loop {
match curr_tree_page {
BPlusTreePage::Internal(internal_page) => {
let next_page_id = internal_page.value_at(0);
let next_page = self.buffer_pool.fetch_page(next_page_id)?;
curr_tree_page = BPlusTreePageCodec::decode(
next_page.read().unwrap().data(),
self.key_schema.clone(),
)?
.0;
let (_, next_tree_page) = self
.buffer_pool
.fetch_tree_page(next_page_id, self.key_schema.clone())?;
curr_tree_page = next_tree_page;
}
BPlusTreePage::Leaf(leaf_page) => {
return Ok(leaf_page);
Expand Down Expand Up @@ -626,12 +606,11 @@ impl TreeIndexIterator {
if next_page_id == INVALID_PAGE_ID {
Ok(false)
} else {
let next_page = self.index.buffer_pool.fetch_page(next_page_id)?;
self.leaf_page = BPlusTreeLeafPageCodec::decode(
next_page.read().unwrap().data(),
self.index.key_schema.clone(),
)?
.0;
let (_, next_leaf_page) = self
.index
.buffer_pool
.fetch_tree_leaf_page(next_page_id, self.index.key_schema.clone())?;
self.leaf_page = next_leaf_page;
Ok(true)
}
}
Expand Down
Loading

0 comments on commit 11c10e6

Please sign in to comment.