Commit 15bdfeeb authored by Marko Mäkelä's avatar Marko Mäkelä

Remove trx_sys_t::pending_purge_rseg_array.

In MySQL 5.7, there is some redundant code for supposedly handling
an upgrade from an earlier version of InnoDB.

An upgrade of InnoDB between major versions should include a
slow shutdown (innodb_fast_shutdown=0) of the previous version.

A comment in trx_lists_init_at_db_start() confused clean shutdown
and slow shutdown. A clean shutdown does not necessarily guarantee
that there are no active transactions. A slow shutdown guarantees
that.

Because there was no code to handle rollback of recovered transactions
that happened to use the rollback segment slots that MySQL 5.7.2
repurposed for temporary undo logs, the upgrade is not working in all
cases, and we may as well remove the code to handle purging.

trx_sys_t::pending_purge_rseg_array: Remove.

trx_undo_get_undo_rec_low(): Define as static. Remove the parameter
is_redo_rseg.

trx_undo_get_undo_rec(), trx_rseg_get_on_id(): Remove the parameter
is_redo_rseg.

trx_rseg_mem_free(): Remove the second parameter.

trx_sys_get_nth_rseg(): Replace with trx_rseg_get_on_id().

trx_rseg_schedule_pending_purge(): Remove.
parent 24cbc8da
......@@ -219,17 +219,6 @@ trx_undo_report_row_operation(
0 if BTR_NO_UNDO_LOG
flag was specified */
MY_ATTRIBUTE((nonnull(3,4,10), warn_unused_result));
/******************************************************************//**
Copies an undo record to heap. This function can be called if we know that
the undo log record exists.
@return own: copy of the record */
trx_undo_rec_t*
trx_undo_get_undo_rec_low(
/*======================*/
roll_ptr_t roll_ptr, /*!< in: roll pointer to record */
mem_heap_t* heap, /*!< in: memory heap where copied */
bool is_redo_rseg) /*!< in: true if redo rseg. */
MY_ATTRIBUTE((nonnull, warn_unused_result));
/** status bit used for trx_undo_prev_version_build() */
......
/*****************************************************************************
Copyright (c) 1996, 2015, Oracle and/or its affiliates. All Rights Reserved.
Copyright (c) 2017, MariaDB Corporation.
This program is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free Software
......@@ -26,7 +27,6 @@ Created 3/26/1996 Heikki Tuuri
#ifndef trx0rseg_h
#define trx0rseg_h
#include "univ.i"
#include "trx0types.h"
#include "trx0sys.h"
#include "fut0lst.h"
......@@ -89,15 +89,16 @@ trx_rsegf_undo_find_free(
/*=====================*/
trx_rsegf_t* rsegf, /*!< in: rollback segment header */
mtr_t* mtr); /*!< in: mtr */
/******************************************************************//**
Looks for a rollback segment, based on the rollback segment id.
/** Get a rollback segment.
@param[in] id rollback segment id
@return rollback segment */
UNIV_INLINE
trx_rseg_t*
trx_rseg_get_on_id(
/*===============*/
ulint id, /*!< in: rollback segment id */
bool is_redo_rseg); /*!< in: true if redo rseg else false. */
trx_rseg_get_on_id(ulint id)
{
ut_a(id < TRX_SYS_N_RSEGS);
return(trx_sys->rseg_array[id]);
}
/** Creates a rollback segment header.
This function is called only when a new rollback segment is created in
......@@ -124,14 +125,10 @@ trx_rseg_array_init(
/*================*/
purge_pq_t* purge_queue); /*!< in: rseg queue */
/***************************************************************************
Free's an instance of the rollback segment in memory. */
/** Free a rollback segment in memory. */
void
trx_rseg_mem_free(
/*==============*/
trx_rseg_t* rseg, /*!< in, own: instance to free */
trx_rseg_t** rseg_array); /*!< out: add rseg reference to this
central array. */
trx_rseg_mem_free(trx_rseg_t* rseg);
/*********************************************************************
Creates a rollback segment. */
trx_rseg_t*
......
/*****************************************************************************
Copyright (c) 1996, 2013, Oracle and/or its affiliates. All Rights Reserved.
Copyright (c) 2017, MariaDB Corporation.
This program is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free Software
......@@ -25,7 +26,6 @@ Created 3/26/1996 Heikki Tuuri
#include "srv0srv.h"
#include "mtr0log.h"
#include "trx0sys.h"
/** Gets a rollback segment header.
@param[in] space space where placed
......@@ -146,28 +146,3 @@ trx_rsegf_undo_find_free(
return(ULINT_UNDEFINED);
}
/******************************************************************//**
Looks for a rollback segment, based on the rollback segment id.
@return rollback segment */
UNIV_INLINE
trx_rseg_t*
trx_rseg_get_on_id(
/*===============*/
ulint id, /*!< in: rollback segment id */
bool is_redo_rseg) /*!< in: true if redo rseg else false. */
{
ut_a(id < TRX_SYS_N_RSEGS);
/* If redo rseg is being requested and id falls in range of
non-redo rseg that is from slot-1....slot-srv_tmp_undo_logs then
server is being upgraded from pre-5.7.2. In such case return
rseg from pending_purge_rseg_array array. */
if (is_redo_rseg && trx_sys_is_noredo_rseg_slot(id)) {
ut_ad(trx_sys->pending_purge_rseg_array[id] != NULL);
return(trx_sys->pending_purge_rseg_array[id]);
}
return(trx_sys->rseg_array[id]);
}
......@@ -89,16 +89,6 @@ trx_sysf_rseg_find_free(
for temp-tablespace as free slots. */
ulint nth_free_slots); /*!< in: allocate nth free slot.
0 means next free slot. */
/***************************************************************//**
Gets the pointer in the nth slot of the rseg array.
@return pointer to rseg object, NULL if slot not in use */
UNIV_INLINE
trx_rseg_t*
trx_sys_get_nth_rseg(
/*=================*/
trx_sys_t* sys, /*!< in: trx system */
ulint n, /*!< in: index of slot */
bool is_redo_rseg); /*!< in: true if redo rseg. */
/**********************************************************************//**
Gets a pointer to the transaction system file copy and x-locks its page.
@return pointer to system file copy, page x-locked */
......@@ -619,14 +609,6 @@ struct trx_sys_t {
transactions), protected by
rseg->mutex */
trx_rseg_t* const pending_purge_rseg_array[TRX_SYS_N_RSEGS];
/*!< Pointer array to rollback segments
between slot-1..slot-srv_tmp_undo_logs
that are now replaced by non-redo
rollback segments. We need them for
scheduling purge if any of the rollback
segment has pending records to purge. */
TrxIdSet rw_trx_set; /*!< Mapping from transaction id
to transaction instance */
......
......@@ -62,31 +62,6 @@ trx_sys_hdr_page(
&& page_id.page_no() == TRX_SYS_PAGE_NO);
}
/***************************************************************//**
Gets the pointer in the nth slot of the rseg array.
@return pointer to rseg object, NULL if slot not in use */
UNIV_INLINE
trx_rseg_t*
trx_sys_get_nth_rseg(
/*=================*/
trx_sys_t* sys, /*!< in: trx system */
ulint n, /*!< in: index of slot */
bool is_redo_rseg) /*!< in: true if redo rseg. */
{
ut_ad(n < TRX_SYS_N_RSEGS);
/* If redo rseg is being requested and id falls in range of
non-redo rseg that is from slot-1....slot-srv_tmp_undo_logs then
server is being upgraded from pre-5.7.2. In such case return
rseg from pending_purge_rseg_array array. */
if (is_redo_rseg && trx_sys_is_noredo_rseg_slot(n)) {
ut_ad(trx_sys->pending_purge_rseg_array[n] != NULL);
return(trx_sys->pending_purge_rseg_array[n]);
}
return(sys->rseg_array[n]);
}
/**********************************************************************//**
Gets a pointer to the transaction system header and x-latches its page.
@return pointer to system header, page x-latched. */
......
......@@ -745,13 +745,7 @@ row_purge_upd_exist_or_extern_func(
&is_insert, &rseg_id,
&page_no, &offset);
/* If table is temp then it can't have its undo log
residing in rollback segment with REDO log enabled. */
bool is_redo_rseg =
dict_table_is_temporary(node->table)
? false : true;
rseg = trx_sys_get_nth_rseg(
trx_sys, rseg_id, is_redo_rseg);
rseg = trx_rseg_get_on_id(rseg_id);
ut_a(rseg != NULL);
ut_a(rseg->id == rseg_id);
......
......@@ -1201,15 +1201,6 @@ trx_purge_truncate_history(
}
}
for (i = 0; i < TRX_SYS_N_RSEGS; ++i) {
trx_rseg_t* rseg = trx_sys->pending_purge_rseg_array[i];
if (rseg != NULL) {
ut_a(rseg->id == i);
trx_purge_truncate_rseg_history(rseg, limit);
}
}
/* UNDO tablespace truncate. We will try to truncate as much as we
can (greedy approach). This will ensure when the server is idle we
try and truncate all the UNDO tablespaces. */
......
......@@ -2104,12 +2104,12 @@ trx_undo_report_row_operation(
Copies an undo record to heap. This function can be called if we know that
the undo log record exists.
@return own: copy of the record */
static
trx_undo_rec_t*
trx_undo_get_undo_rec_low(
/*======================*/
roll_ptr_t roll_ptr, /*!< in: roll pointer to record */
mem_heap_t* heap, /*!< in: memory heap where copied */
bool is_redo_rseg) /*!< in: true if redo rseg. */
mem_heap_t* heap) /*!< in: memory heap where copied */
{
trx_undo_rec_t* undo_rec;
ulint rseg_id;
......@@ -2122,7 +2122,7 @@ trx_undo_get_undo_rec_low(
trx_undo_decode_roll_ptr(roll_ptr, &is_insert, &rseg_id, &page_no,
&offset);
rseg = trx_rseg_get_on_id(rseg_id, is_redo_rseg);
rseg = trx_rseg_get_on_id(rseg_id);
mtr_start(&mtr);
......@@ -2144,7 +2144,6 @@ Copies an undo record to heap.
the roll pointer: it points to an
undo log of this transaction
@param[in] heap memory heap where copied
@param[in] is_redo_rseg true if redo rseg.
@param[in] name table name
@param[out] undo_rec own: copy of the record
@retval true if the undo log has been
......@@ -2158,7 +2157,6 @@ trx_undo_get_undo_rec(
roll_ptr_t roll_ptr,
trx_id_t trx_id,
mem_heap_t* heap,
bool is_redo_rseg,
const table_name_t& name,
trx_undo_rec_t** undo_rec)
{
......@@ -2168,8 +2166,7 @@ trx_undo_get_undo_rec(
missing_history = purge_sys->view.changes_visible(trx_id, name);
if (!missing_history) {
*undo_rec = trx_undo_get_undo_rec_low(
roll_ptr, heap, is_redo_rseg);
*undo_rec = trx_undo_get_undo_rec_low(roll_ptr, heap);
}
rw_lock_s_unlock(&purge_sys->latch);
......@@ -2252,17 +2249,11 @@ trx_undo_prev_version_build(
rec_trx_id = row_get_rec_trx_id(rec, index, offsets);
/* REDO rollback segment are used only for non-temporary objects.
For temporary objects NON-REDO rollback segments are used. */
bool is_redo_rseg =
dict_table_is_temporary(index->table) ? false : true;
if (trx_undo_get_undo_rec(
roll_ptr, rec_trx_id, heap, is_redo_rseg,
index->table->name, &undo_rec)) {
roll_ptr, rec_trx_id, heap, index->table->name, &undo_rec)) {
if (v_status & TRX_UNDO_PREV_IN_PURGE) {
/* We are fetching the record being purged */
undo_rec = trx_undo_get_undo_rec_low(
roll_ptr, heap, is_redo_rseg);
undo_rec = trx_undo_get_undo_rec_low(roll_ptr, heap);
} else {
/* The undo record may already have been purged,
during purge or semi-consistent read. */
......
/*****************************************************************************
Copyright (c) 1996, 2015, Oracle and/or its affiliates. All Rights Reserved.
Copyright (c) 2017, MariaDB Corporation.
This program is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free Software
......@@ -116,14 +117,9 @@ trx_rseg_header_create(
return(page_no);
}
/***********************************************************************//**
Free's an instance of the rollback segment in memory. */
/** Free a rollback segment in memory. */
void
trx_rseg_mem_free(
/*==============*/
trx_rseg_t* rseg, /* in, own: instance to free */
trx_rseg_t** rseg_array) /*!< out: add rseg reference to this
central array. */
trx_rseg_mem_free(trx_rseg_t* rseg)
{
trx_undo_t* undo;
trx_undo_t* next_undo;
......@@ -160,9 +156,6 @@ trx_rseg_mem_free(
trx_undo_mem_free(undo);
}
ut_a(*((trx_rseg_t**) rseg_array + rseg->id) == rseg);
*((trx_rseg_t**) rseg_array + rseg->id) = NULL;
ut_free(rseg);
}
......@@ -269,49 +262,6 @@ trx_rseg_mem_create(
return(rseg);
}
/********************************************************************
Check if rseg in given slot needs to be scheduled for purge. */
static
void
trx_rseg_schedule_pending_purge(
/*============================*/
trx_sysf_t* sys_header, /*!< in: trx system header */
purge_pq_t* purge_queue, /*!< in/out: rseg queue */
ulint slot, /*!< in: check rseg from given slot. */
mtr_t* mtr) /*!< in: mtr */
{
ulint page_no;
ulint space;
page_no = trx_sysf_rseg_get_page_no(sys_header, slot, mtr);
space = trx_sysf_rseg_get_space(sys_header, slot, mtr);
if (page_no != FIL_NULL
&& is_system_or_undo_tablespace(space)) {
/* rseg resides in system or undo tablespace and so
this is an upgrade scenario. trx_rseg_mem_create
will add rseg to purge queue if needed. */
trx_rseg_t* rseg = NULL;
bool found = true;
const page_size_t& page_size
= is_system_tablespace(space)
? univ_page_size
: fil_space_get_page_size(space, &found);
ut_ad(found);
trx_rseg_t** rseg_array =
((trx_rseg_t**) trx_sys->pending_purge_rseg_array);
rseg = trx_rseg_mem_create(
slot, space, page_no, page_size,
purge_queue, rseg_array, mtr);
ut_a(rseg->id == slot);
}
}
/********************************************************************
Creates the memory copies for the rollback segments and initializes the
rseg array in trx_sys at a database startup. */
......@@ -332,22 +282,11 @@ trx_rseg_create_instance(
page_no = trx_sysf_rseg_get_page_no(sys_header, i, &mtr);
/* Slot-1....Slot-n are reserved for non-redo rsegs.
Non-redo rsegs are recreated on server re-start so
avoid initializing the existing non-redo rsegs. */
if (trx_sys_is_noredo_rseg_slot(i)) {
/* If this is an upgrade scenario then existing rsegs
in range from slot-1....slot-n needs to be scheduled
for purge if there are pending purge operation. */
trx_rseg_schedule_pending_purge(
sys_header, purge_queue, i, &mtr);
} else if (page_no != FIL_NULL) {
if (page_no != FIL_NULL) {
ulint space;
trx_rseg_t* rseg = NULL;
ut_a(!trx_rseg_get_on_id(i, true));
ut_a(!trx_rseg_get_on_id(i));
space = trx_sysf_rseg_get_space(sys_header, i, &mtr);
......
......@@ -1108,28 +1108,10 @@ trx_sys_close(void)
}
/* There can't be any active transactions. */
trx_rseg_t** rseg_array = static_cast<trx_rseg_t**>(
trx_sys->rseg_array);
for (ulint i = 0; i < TRX_SYS_N_RSEGS; ++i) {
trx_rseg_t* rseg;
rseg = trx_sys->rseg_array[i];
if (rseg != NULL) {
trx_rseg_mem_free(rseg, rseg_array);
}
}
rseg_array = ((trx_rseg_t**) trx_sys->pending_purge_rseg_array);
for (ulint i = 0; i < TRX_SYS_N_RSEGS; ++i) {
trx_rseg_t* rseg;
rseg = trx_sys->pending_purge_rseg_array[i];
if (rseg != NULL) {
trx_rseg_mem_free(rseg, rseg_array);
if (trx_rseg_t* rseg = trx_sys->rseg_array[i]) {
trx_rseg_mem_free(rseg);
}
}
......
......@@ -1020,8 +1020,6 @@ trx_lists_init_at_db_start(void)
ut_a(srv_is_being_started);
/* Look from the rollback segments if there exist undo logs for
transactions. Upgrade demands clean shutdown and so there is
not need to look at pending_purge_rseg_array for rollbacking
transactions. */
for (ulint i = 0; i < TRX_SYS_N_RSEGS; ++i) {
......
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