Skip to content

Commit

Permalink
MDEV-16678 Prefer MDL to dict_sys.latch for innodb background tasks
Browse files Browse the repository at this point in the history
Use std::queue backed by std::deque instead of list because it does less
allocations which still having O(1) push and pop operations.

Also store trx_purge_rec_t directly, because its only 16 bytes and allocating
it is to wasteful. This should be faster.

purge_node_t::purge_node_t: container is already empty after creation

purge_node_t::end(): replace clearing container with assertion that it's clear
  • Loading branch information
kevgs committed Dec 11, 2019
1 parent adb117c commit f4b4284
Show file tree
Hide file tree
Showing 3 changed files with 14 additions and 19 deletions.
7 changes: 3 additions & 4 deletions storage/innobase/include/row0purge.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ Created 3/14/1997 Heikki Tuuri
#include "row0types.h"
#include "row0mysql.h"
#include "mysqld.h"
#include <list>
#include <queue>

class MDL_ticket;
/** Determines if it is possible to remove a secondary index entry.
Expand Down Expand Up @@ -150,7 +150,7 @@ struct purge_node_t{
int mdl_hold_recs;

/** Undo recs to purge */
std::list<trx_purge_rec_t*> undo_recs;
std::queue<trx_purge_rec_t> undo_recs;

/** Constructor */
explicit purge_node_t(que_thr_t* parent) :
Expand All @@ -166,7 +166,6 @@ struct purge_node_t{
purge_thd(NULL),
mdl_hold_recs(0)
{
undo_recs.clear();
}

#ifdef UNIV_DEBUG
Expand Down Expand Up @@ -258,7 +257,7 @@ struct purge_node_t{
{
DBUG_ASSERT(common.type == QUE_NODE_PURGE);
close_table();
undo_recs.clear();
ut_ad(undo_recs.empty());
ut_d(in_progress= false);
purge_thd= nullptr;
mem_heap_empty(heap);
Expand Down
9 changes: 4 additions & 5 deletions storage/innobase/row/row0purge.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1155,12 +1155,11 @@ row_purge_step(
node->start();

if (!node->undo_recs.empty()) {
trx_purge_rec_t* purge_rec =
node->undo_recs.front();
node->undo_recs.pop_front();
node->roll_ptr = purge_rec->roll_ptr;
trx_purge_rec_t purge_rec = node->undo_recs.front();
node->undo_recs.pop();
node->roll_ptr = purge_rec.roll_ptr;

row_purge(node, purge_rec->undo_rec, thr);
row_purge(node, purge_rec.undo_rec, thr);

if (node->undo_recs.empty()) {
row_purge_end(thr);
Expand Down
17 changes: 7 additions & 10 deletions storage/innobase/trx/trx0purge.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1141,17 +1141,14 @@ trx_purge_attach_undo_recs(ulint n_purge_threads)

while (UNIV_LIKELY(srv_undo_sources) || !srv_fast_shutdown) {
purge_node_t* node;
trx_purge_rec_t* purge_rec;
trx_purge_rec_t purge_rec;

ut_a(!thr->is_active);

/* Get the purge node. */
node = (purge_node_t*) thr->child;
ut_a(que_node_get_type(node) == QUE_NODE_PURGE);

purge_rec = static_cast<trx_purge_rec_t*>(
mem_heap_zalloc(purge_sys.heap, sizeof(*purge_rec)));

/* Track the max {trx_id, undo_no} for truncating the
UNDO logs once we have purged the records. */

Expand All @@ -1160,18 +1157,18 @@ trx_purge_attach_undo_recs(ulint n_purge_threads)
}

/* Fetch the next record, and advance the purge_sys.tail. */
purge_rec->undo_rec = trx_purge_fetch_next_rec(
&purge_rec->roll_ptr, &n_pages_handled,
purge_rec.undo_rec = trx_purge_fetch_next_rec(
&purge_rec.roll_ptr, &n_pages_handled,
purge_sys.heap);

if (purge_rec->undo_rec == NULL) {
if (purge_rec.undo_rec == NULL) {
break;
} else if (purge_rec->undo_rec == &trx_purge_dummy_rec) {
} else if (purge_rec.undo_rec == &trx_purge_dummy_rec) {
continue;
}

table_id_t table_id = trx_undo_rec_get_table_id(
purge_rec->undo_rec);
purge_rec.undo_rec);

auto it = table_id_map.find(table_id);

Expand All @@ -1189,7 +1186,7 @@ trx_purge_attach_undo_recs(ulint n_purge_threads)
table_id_map.insert({table_id, node});
}

node->undo_recs.push_back(purge_rec);
node->undo_recs.push(purge_rec);

if (n_pages_handled >= batch_size) {
break;
Expand Down

0 comments on commit f4b4284

Please sign in to comment.