Commit f74023b9 authored by Marko Mäkelä's avatar Marko Mäkelä

MDEV-15090 Reduce the overhead of writing undo log records

Remove unnecessary repeated lookups for undo pages.

trx_undo_assign(), trx_undo_assign_low(), trx_undo_seg_create(),
trx_undo_create(): Return the undo log block to the caller.
parent 5d3c3b49
...@@ -255,28 +255,25 @@ trx_undo_lists_init( ...@@ -255,28 +255,25 @@ trx_undo_lists_init(
/** Assign an undo log for a persistent transaction. /** Assign an undo log for a persistent transaction.
A new undo log is created or a cached undo log reused. A new undo log is created or a cached undo log reused.
@param[in,out] trx transaction @param[in,out] trx transaction
@param[out] err error code
@param[in,out] mtr mini-transaction @param[in,out] mtr mini-transaction
@retval DB_SUCCESS on success @return the undo log block
@retval DB_TOO_MANY_CONCURRENT_TRXS @retval NULL on error */
@retval DB_OUT_OF_FILE_SPACE buf_block_t*
@retval DB_READ_ONLY trx_undo_assign(trx_t* trx, dberr_t* err, mtr_t* mtr)
@retval DB_OUT_OF_MEMORY */ MY_ATTRIBUTE((nonnull));
dberr_t
trx_undo_assign(trx_t* trx, mtr_t* mtr)
MY_ATTRIBUTE((nonnull, warn_unused_result));
/** Assign an undo log for a transaction. /** Assign an undo log for a transaction.
A new undo log is created or a cached undo log reused. A new undo log is created or a cached undo log reused.
@param[in,out] trx transaction @param[in,out] trx transaction
@param[in] rseg rollback segment @param[in] rseg rollback segment
@param[out] undo the undo log @param[out] undo the undo log
@param[out] err error code
@param[in,out] mtr mini-transaction @param[in,out] mtr mini-transaction
@retval DB_SUCCESS on success @return the undo log block
@retval DB_TOO_MANY_CONCURRENT_TRXS @retval NULL on error */
@retval DB_OUT_OF_FILE_SPACE buf_block_t*
@retval DB_READ_ONLY trx_undo_assign_low(trx_t* trx, trx_rseg_t* rseg, trx_undo_t** undo,
@retval DB_OUT_OF_MEMORY */ dberr_t* err, mtr_t* mtr)
dberr_t
trx_undo_assign_low(trx_t* trx, trx_rseg_t* rseg, trx_undo_t** undo, mtr_t*mtr)
MY_ATTRIBUTE((nonnull, warn_unused_result)); MY_ATTRIBUTE((nonnull, warn_unused_result));
/******************************************************************//** /******************************************************************//**
Sets the state of the undo log segment at a transaction finish. Sets the state of the undo log segment at a transaction finish.
......
...@@ -3403,7 +3403,7 @@ row_import_for_mysql( ...@@ -3403,7 +3403,7 @@ row_import_for_mysql(
{ {
mtr_t mtr; mtr_t mtr;
mtr.start(); mtr.start();
err = trx_undo_assign(trx, &mtr); trx_undo_assign(trx, &err, &mtr);
mtr.commit(); mtr.commit();
} }
......
...@@ -1823,7 +1823,7 @@ row_truncate_table_for_mysql( ...@@ -1823,7 +1823,7 @@ row_truncate_table_for_mysql(
mutex_enter(&trx->undo_mutex); mutex_enter(&trx->undo_mutex);
mtr_t mtr; mtr_t mtr;
mtr.start(); mtr.start();
err = trx_undo_assign(trx, &mtr); trx_undo_assign(trx, &err, &mtr);
mtr.commit(); mtr.commit();
mutex_exit(&trx->undo_mutex); mutex_exit(&trx->undo_mutex);
......
...@@ -1902,22 +1902,15 @@ trx_undo_report_rename(trx_t* trx, const dict_table_t* table) ...@@ -1902,22 +1902,15 @@ trx_undo_report_rename(trx_t* trx, const dict_table_t* table)
ut_ad(!table->is_temporary()); ut_ad(!table->is_temporary());
mtr_t mtr; mtr_t mtr;
dberr_t err;
mtr.start(); mtr.start();
mutex_enter(&trx->undo_mutex); mutex_enter(&trx->undo_mutex);
dberr_t err = trx_undo_assign(trx, &mtr); if (buf_block_t* block = trx_undo_assign(trx, &err, &mtr)) {
ut_ad((err == DB_SUCCESS) == (trx->rsegs.m_redo.undo != NULL)); trx_undo_t* undo = trx->rsegs.m_redo.undo;
if (trx_undo_t* undo = trx->rsegs.m_redo.undo) { ut_ad(err == DB_SUCCESS);
buf_block_t* block = buf_page_get_gen( ut_ad(undo);
page_id_t(undo->space, undo->last_page_no), for (ut_d(int loop_count = 0);;) {
univ_page_size, RW_X_LATCH,
buf_pool_is_obsolete(undo->withdraw_clock)
? NULL : undo->guess_block,
BUF_GET, __FILE__, __LINE__, &mtr, &err);
ut_ad((err == DB_SUCCESS) == !!block);
for (ut_d(int loop_count = 0); block;) {
ut_ad(++loop_count < 2); ut_ad(++loop_count < 2);
buf_block_dbg_add_level(block, SYNC_TRX_UNDO_PAGE);
ut_ad(undo->last_page_no == block->page.id.page_no()); ut_ad(undo->last_page_no == block->page.id.page_no());
if (ulint offset = trx_undo_page_report_rename( if (ulint offset = trx_undo_page_report_rename(
...@@ -1981,8 +1974,6 @@ trx_undo_report_row_operation( ...@@ -1981,8 +1974,6 @@ trx_undo_report_row_operation(
undo log record */ undo log record */
{ {
trx_t* trx; trx_t* trx;
ulint page_no;
buf_block_t* undo_block;
mtr_t mtr; mtr_t mtr;
#ifdef UNIV_DEBUG #ifdef UNIV_DEBUG
int loop_count = 0; int loop_count = 0;
...@@ -2017,27 +2008,19 @@ trx_undo_report_row_operation( ...@@ -2017,27 +2008,19 @@ trx_undo_report_row_operation(
} }
mutex_enter(&trx->undo_mutex); mutex_enter(&trx->undo_mutex);
dberr_t err = *pundo dberr_t err;
? DB_SUCCESS : trx_undo_assign_low(trx, rseg, pundo, &mtr); buf_block_t* undo_block = trx_undo_assign_low(trx, rseg, pundo,
&err, &mtr);
trx_undo_t* undo = *pundo; trx_undo_t* undo = *pundo;
ut_ad((err == DB_SUCCESS) == (undo != NULL)); ut_ad((err == DB_SUCCESS) == (undo_block != NULL));
if (undo == NULL) { if (undo_block == NULL) {
goto err_exit; goto err_exit;
} }
page_no = undo->last_page_no; ut_ad(undo != NULL);
undo_block = buf_page_get_gen(
page_id_t(undo->space, page_no), univ_page_size, RW_X_LATCH,
buf_pool_is_obsolete(undo->withdraw_clock)
? NULL : undo->guess_block, BUF_GET, __FILE__, __LINE__,
&mtr, &err);
buf_block_dbg_add_level(undo_block, SYNC_TRX_UNDO_PAGE);
do { do {
ut_ad(page_no == undo_block->page.id.page_no());
page_t* undo_page = buf_block_get_frame(undo_block); page_t* undo_page = buf_block_get_frame(undo_block);
ulint offset = !rec ulint offset = !rec
? trx_undo_page_report_insert( ? trx_undo_page_report_insert(
...@@ -2082,7 +2065,7 @@ trx_undo_report_row_operation( ...@@ -2082,7 +2065,7 @@ trx_undo_report_row_operation(
mtr_commit(&mtr); mtr_commit(&mtr);
undo->empty = FALSE; undo->empty = FALSE;
undo->top_page_no = page_no; undo->top_page_no = undo_block->page.id.page_no();
undo->top_offset = offset; undo->top_offset = offset;
undo->top_undo_no = trx->undo_no++; undo->top_undo_no = trx->undo_no++;
undo->guess_block = undo_block; undo->guess_block = undo_block;
...@@ -2113,11 +2096,11 @@ trx_undo_report_row_operation( ...@@ -2113,11 +2096,11 @@ trx_undo_report_row_operation(
} }
*roll_ptr = trx_undo_build_roll_ptr( *roll_ptr = trx_undo_build_roll_ptr(
!rec, rseg->id, page_no, offset); !rec, rseg->id, undo->top_page_no, offset);
return(DB_SUCCESS); return(DB_SUCCESS);
} }
ut_ad(page_no == undo->last_page_no); ut_ad(undo_block->page.id.page_no() == undo->last_page_no);
/* We have to extend the undo log by one page */ /* We have to extend the undo log by one page */
...@@ -2129,7 +2112,6 @@ trx_undo_report_row_operation( ...@@ -2129,7 +2112,6 @@ trx_undo_report_row_operation(
} }
undo_block = trx_undo_add_page(trx, undo, &mtr); undo_block = trx_undo_add_page(trx, undo, &mtr);
page_no = undo->last_page_no;
DBUG_EXECUTE_IF("ib_err_ins_undo_page_add_failure", DBUG_EXECUTE_IF("ib_err_ins_undo_page_add_failure",
undo_block = NULL;); undo_block = NULL;);
......
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment