Revert "MDEV-12266: Remove lookups when dropping indexes"
This reverts commit d2660362920a82588508028f263dad9c16f08865. The patch would cause a crash when DROP TABLE is executed and the .ibd file is missing. It is not easy to fix this; there is some delicate logic in fil_space_get_page_size().
This commit is contained in:
parent
e895041ba9
commit
04bac13b30
@ -1140,8 +1140,8 @@ btr_free_root_invalidate(
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** Prepare to free a B-tree.
|
/** Prepare to free a B-tree.
|
||||||
@param[in,out] space tablespace
|
@param[in] page_id page id
|
||||||
@param[in] page root page number
|
@param[in] page_size page size
|
||||||
@param[in] index_id PAGE_INDEX_ID contents
|
@param[in] index_id PAGE_INDEX_ID contents
|
||||||
@param[in,out] mtr mini-transaction
|
@param[in,out] mtr mini-transaction
|
||||||
@return root block, to invoke btr_free_but_not_root() and btr_free_root()
|
@return root block, to invoke btr_free_but_not_root() and btr_free_root()
|
||||||
@ -1149,32 +1149,32 @@ btr_free_root_invalidate(
|
|||||||
static MY_ATTRIBUTE((warn_unused_result))
|
static MY_ATTRIBUTE((warn_unused_result))
|
||||||
buf_block_t*
|
buf_block_t*
|
||||||
btr_free_root_check(
|
btr_free_root_check(
|
||||||
fil_space_t* space,
|
const page_id_t& page_id,
|
||||||
ulint page,
|
const page_size_t& page_size,
|
||||||
index_id_t index_id,
|
index_id_t index_id,
|
||||||
mtr_t* mtr)
|
mtr_t* mtr)
|
||||||
{
|
{
|
||||||
ut_ad(space->purpose == FIL_TYPE_TABLESPACE);
|
ut_ad(page_id.space() != SRV_TMP_SPACE_ID);
|
||||||
ut_ad(index_id != BTR_FREED_INDEX_ID);
|
ut_ad(index_id != BTR_FREED_INDEX_ID);
|
||||||
|
|
||||||
if (buf_block_t* block = buf_page_get(
|
buf_block_t* block = buf_page_get(
|
||||||
page_id_t(space->id, page), page_size_t(space->flags),
|
page_id, page_size, RW_X_LATCH, mtr);
|
||||||
RW_X_LATCH, mtr)) {
|
|
||||||
|
if (block) {
|
||||||
buf_block_dbg_add_level(block, SYNC_TREE_NODE);
|
buf_block_dbg_add_level(block, SYNC_TREE_NODE);
|
||||||
|
|
||||||
if (!fil_page_index_page_check(block->frame)
|
if (fil_page_index_page_check(block->frame)
|
||||||
|| index_id != btr_page_get_index_id(block->frame)) {
|
&& index_id == btr_page_get_index_id(block->frame)) {
|
||||||
return NULL;
|
/* This should be a root page.
|
||||||
|
It should not be possible to reassign the same
|
||||||
|
index_id for some other index in the tablespace. */
|
||||||
|
ut_ad(page_is_root(block->frame));
|
||||||
|
} else {
|
||||||
|
block = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* This should be a root page.
|
|
||||||
It should not be possible to reassign the same
|
|
||||||
index_id for some other index in the tablespace. */
|
|
||||||
ut_ad(page_is_root(block->frame));
|
|
||||||
return block;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return NULL;
|
return(block);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Create the root node for a new index tree.
|
/** Create the root node for a new index tree.
|
||||||
@ -1348,26 +1348,29 @@ btr_create(
|
|||||||
|
|
||||||
/** Free a B-tree except the root page. The root page MUST be freed after
|
/** Free a B-tree except the root page. The root page MUST be freed after
|
||||||
this by calling btr_free_root.
|
this by calling btr_free_root.
|
||||||
@param[in,out] space tablespace, or NULL
|
|
||||||
@param[in,out] block root page
|
@param[in,out] block root page
|
||||||
@param[in] log_mode mtr logging mode */
|
@param[in] log_mode mtr logging mode */
|
||||||
static
|
static
|
||||||
void
|
void
|
||||||
btr_free_but_not_root(
|
btr_free_but_not_root(
|
||||||
fil_space_t* space,
|
|
||||||
buf_block_t* block,
|
buf_block_t* block,
|
||||||
mtr_log_t log_mode)
|
mtr_log_t log_mode)
|
||||||
{
|
{
|
||||||
ibool finished;
|
ibool finished;
|
||||||
mtr_t mtr;
|
mtr_t mtr;
|
||||||
|
|
||||||
|
ut_ad(page_is_root(block->frame));
|
||||||
|
leaf_loop:
|
||||||
|
mtr_start(&mtr);
|
||||||
|
mtr_set_log_mode(&mtr, log_mode);
|
||||||
|
mtr.set_named_space_id(block->page.id.space());
|
||||||
|
|
||||||
page_t* root = block->frame;
|
page_t* root = block->frame;
|
||||||
|
|
||||||
ut_ad(page_is_root(root));
|
if (!root) {
|
||||||
ut_ad(!space || block->page.id.space() == space->id);
|
mtr_commit(&mtr);
|
||||||
leaf_loop:
|
return;
|
||||||
mtr.start();
|
}
|
||||||
mtr.set_log_mode(log_mode);
|
|
||||||
if (space) mtr.set_named_space(space);
|
|
||||||
|
|
||||||
#ifdef UNIV_BTR_DEBUG
|
#ifdef UNIV_BTR_DEBUG
|
||||||
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_LEAF
|
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_LEAF
|
||||||
@ -1381,15 +1384,18 @@ leaf_loop:
|
|||||||
|
|
||||||
finished = fseg_free_step(root + PAGE_HEADER + PAGE_BTR_SEG_LEAF,
|
finished = fseg_free_step(root + PAGE_HEADER + PAGE_BTR_SEG_LEAF,
|
||||||
true, &mtr);
|
true, &mtr);
|
||||||
mtr.commit();
|
mtr_commit(&mtr);
|
||||||
|
|
||||||
if (!finished) {
|
if (!finished) {
|
||||||
|
|
||||||
goto leaf_loop;
|
goto leaf_loop;
|
||||||
}
|
}
|
||||||
top_loop:
|
top_loop:
|
||||||
mtr.start();
|
mtr_start(&mtr);
|
||||||
mtr.set_log_mode(log_mode);
|
mtr_set_log_mode(&mtr, log_mode);
|
||||||
if (space) mtr.set_named_space(space);
|
mtr.set_named_space_id(block->page.id.space());
|
||||||
|
|
||||||
|
root = block->frame;
|
||||||
|
|
||||||
#ifdef UNIV_BTR_DEBUG
|
#ifdef UNIV_BTR_DEBUG
|
||||||
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_TOP
|
ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_TOP
|
||||||
@ -1398,7 +1404,7 @@ top_loop:
|
|||||||
|
|
||||||
finished = fseg_free_step_not_header(
|
finished = fseg_free_step_not_header(
|
||||||
root + PAGE_HEADER + PAGE_BTR_SEG_TOP, true, &mtr);
|
root + PAGE_HEADER + PAGE_BTR_SEG_TOP, true, &mtr);
|
||||||
mtr.commit();
|
mtr_commit(&mtr);
|
||||||
|
|
||||||
if (!finished) {
|
if (!finished) {
|
||||||
goto top_loop;
|
goto top_loop;
|
||||||
@ -1406,25 +1412,29 @@ top_loop:
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** Free a persistent index tree if it exists.
|
/** Free a persistent index tree if it exists.
|
||||||
@param[in,out] space tablespace
|
@param[in] page_id root page id
|
||||||
@param[in] page root page number
|
@param[in] page_size page size
|
||||||
@param[in] index_id PAGE_INDEX_ID contents
|
@param[in] index_id PAGE_INDEX_ID contents
|
||||||
@param[in,out] mtr mini-transaction */
|
@param[in,out] mtr mini-transaction */
|
||||||
void
|
void
|
||||||
btr_free_if_exists(
|
btr_free_if_exists(
|
||||||
fil_space_t* space,
|
const page_id_t& page_id,
|
||||||
ulint page,
|
const page_size_t& page_size,
|
||||||
index_id_t index_id,
|
index_id_t index_id,
|
||||||
mtr_t* mtr)
|
mtr_t* mtr)
|
||||||
{
|
{
|
||||||
if (buf_block_t* root = btr_free_root_check(space, page, index_id,
|
buf_block_t* root = btr_free_root_check(
|
||||||
mtr)) {
|
page_id, page_size, index_id, mtr);
|
||||||
ut_ad(page_is_root(root->frame));
|
|
||||||
btr_free_but_not_root(space, root, mtr->get_log_mode());
|
if (root == NULL) {
|
||||||
mtr->set_named_space(space);
|
return;
|
||||||
btr_free_root(root, mtr);
|
|
||||||
btr_free_root_invalidate(root, mtr);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ut_ad(page_is_root(root->frame));
|
||||||
|
btr_free_but_not_root(root, mtr->get_log_mode());
|
||||||
|
mtr->set_named_space_id(page_id.space());
|
||||||
|
btr_free_root(root, mtr);
|
||||||
|
btr_free_root_invalidate(root, mtr);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Free an index tree in a temporary tablespace or during TRUNCATE TABLE.
|
/** Free an index tree in a temporary tablespace or during TRUNCATE TABLE.
|
||||||
@ -1439,10 +1449,13 @@ btr_free(
|
|||||||
mtr.start();
|
mtr.start();
|
||||||
mtr.set_log_mode(MTR_LOG_NO_REDO);
|
mtr.set_log_mode(MTR_LOG_NO_REDO);
|
||||||
|
|
||||||
if (buf_block_t* block = buf_page_get(page_id, page_size, RW_X_LATCH,
|
buf_block_t* block = buf_page_get(
|
||||||
&mtr)) {
|
page_id, page_size, RW_X_LATCH, &mtr);
|
||||||
|
|
||||||
|
if (block) {
|
||||||
ut_ad(page_is_root(block->frame));
|
ut_ad(page_is_root(block->frame));
|
||||||
btr_free_but_not_root(NULL, block, MTR_LOG_NO_REDO);
|
|
||||||
|
btr_free_but_not_root(block, MTR_LOG_NO_REDO);
|
||||||
btr_free_root(block, &mtr);
|
btr_free_root(block, &mtr);
|
||||||
}
|
}
|
||||||
mtr.commit();
|
mtr.commit();
|
||||||
|
@ -911,6 +911,7 @@ dict_drop_index_tree(
|
|||||||
{
|
{
|
||||||
const byte* ptr;
|
const byte* ptr;
|
||||||
ulint len;
|
ulint len;
|
||||||
|
ulint space;
|
||||||
ulint root_page_no;
|
ulint root_page_no;
|
||||||
|
|
||||||
ut_ad(mutex_own(&dict_sys->mutex));
|
ut_ad(mutex_own(&dict_sys->mutex));
|
||||||
@ -937,36 +938,35 @@ dict_drop_index_tree(
|
|||||||
|
|
||||||
ut_ad(len == 4);
|
ut_ad(len == 4);
|
||||||
|
|
||||||
ulint space_id = mach_read_from_4(ptr);
|
space = mtr_read_ulint(ptr, MLOG_4BYTES, mtr);
|
||||||
|
|
||||||
ptr = rec_get_nth_field_old(
|
ptr = rec_get_nth_field_old(
|
||||||
rec, DICT_FLD__SYS_INDEXES__ID, &len);
|
rec, DICT_FLD__SYS_INDEXES__ID, &len);
|
||||||
|
|
||||||
ut_ad(len == 8);
|
ut_ad(len == 8);
|
||||||
|
|
||||||
|
bool found;
|
||||||
|
const page_size_t page_size(fil_space_get_page_size(space,
|
||||||
|
&found));
|
||||||
|
|
||||||
|
if (!found) {
|
||||||
|
/* It is a single table tablespace and the .ibd file is
|
||||||
|
missing: do nothing */
|
||||||
|
|
||||||
|
return(false);
|
||||||
|
}
|
||||||
|
|
||||||
/* If tablespace is scheduled for truncate, do not try to drop
|
/* If tablespace is scheduled for truncate, do not try to drop
|
||||||
the indexes in that tablespace. There is a truncate fixup action
|
the indexes in that tablespace. There is a truncate fixup action
|
||||||
which will take care of it. */
|
which will take care of it. */
|
||||||
if (srv_is_tablespace_truncated(space_id)) {
|
if (srv_is_tablespace_truncated(space)) {
|
||||||
return false;
|
return(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* We cannot use fil_space_acquire_silent() here,
|
btr_free_if_exists(page_id_t(space, root_page_no), page_size,
|
||||||
because it would return NULL due to the pending
|
mach_read_from_8(ptr), mtr);
|
||||||
DROP or TRUNCATE operation. */
|
|
||||||
mutex_enter(&fil_system.mutex);
|
|
||||||
|
|
||||||
if (fil_space_t* space = fil_space_get_by_id(space_id)) {
|
return(true);
|
||||||
space->n_pending_ops++;
|
|
||||||
mutex_exit(&fil_system.mutex);
|
|
||||||
btr_free_if_exists(space, root_page_no,
|
|
||||||
mach_read_from_8(ptr), mtr);
|
|
||||||
fil_space_release(space);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
mutex_exit(&fil_system.mutex);
|
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*******************************************************************//**
|
/*******************************************************************//**
|
||||||
|
@ -373,16 +373,16 @@ btr_create(
|
|||||||
mtr_t* mtr);
|
mtr_t* mtr);
|
||||||
|
|
||||||
/** Free a persistent index tree if it exists.
|
/** Free a persistent index tree if it exists.
|
||||||
@param[in,out] space tablespace
|
@param[in] page_id root page id
|
||||||
@param[in] page root page number
|
@param[in] page_size page size
|
||||||
@param[in] index_id PAGE_INDEX_ID contents
|
@param[in] index_id PAGE_INDEX_ID contents
|
||||||
@param[in,out] mtr mini-transaction */
|
@param[in,out] mtr mini-transaction */
|
||||||
void
|
void
|
||||||
btr_free_if_exists(
|
btr_free_if_exists(
|
||||||
fil_space_t* space,
|
const page_id_t& page_id,
|
||||||
ulint page,
|
const page_size_t& page_size,
|
||||||
index_id_t index_id,
|
index_id_t index_id,
|
||||||
mtr_t* mtr);
|
mtr_t* mtr);
|
||||||
|
|
||||||
/** Free an index tree in a temporary tablespace or during TRUNCATE TABLE.
|
/** Free an index tree in a temporary tablespace or during TRUNCATE TABLE.
|
||||||
@param[in] page_id root page id
|
@param[in] page_id root page id
|
||||||
|
@ -3021,8 +3021,10 @@ void truncate_t::drop_indexes(fil_space_t* space) const
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (root_page_no != FIL_NULL) {
|
if (root_page_no != FIL_NULL) {
|
||||||
btr_free_if_exists(space, root_page_no, it->m_id,
|
const page_id_t root_page_id(space->id, root_page_no);
|
||||||
&mtr);
|
|
||||||
|
btr_free_if_exists(
|
||||||
|
root_page_id, page_size, it->m_id, &mtr);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* If tree is already freed then we might return immediately
|
/* If tree is already freed then we might return immediately
|
||||||
|
Loading…
x
Reference in New Issue
Block a user