1
0
mirror of https://github.com/MariaDB/server.git synced 2025-12-24 11:21:21 +03:00

MDEV-32163 Crash recovery fails after DROP TABLE in system tablespace

fseg_free_extent(): After fsp_free_extent() succeeded, properly
mark the affected pages as freed. We failed to write FREE_PAGE records.

This bug was revealed or caused by
commit e938d7c18f (MDEV-32028).
This commit is contained in:
Marko Mäkelä
2023-09-14 15:17:27 +03:00
parent cb1965bd9d
commit 81e60f1a0a
3 changed files with 43 additions and 2 deletions

View File

@@ -0,0 +1,13 @@
SET GLOBAL
innodb_file_per_table=OFF,
innodb_purge_rseg_truncate_frequency=1,
innodb_immediate_scrub_data_uncompressed=ON;
CREATE TABLE t1(f1 INT NOT NULL, f2 INT NOT NULL,
f3 INT NOT NULL, INDEX(f1),
INDEX(f2), INDEX(f3))ENGINE=InnoDB;
INSERT INTO t1 SELECT seq, seq, seq FROM seq_1_to_16384;
INSERT INTO t1 SELECT seq, seq, seq FROM seq_1_to_16384;
INSERT INTO t1 SELECT seq, seq, seq FROM seq_1_to_16384;
DROP TABLE t1;
SET GLOBAL innodb_max_purge_lag_wait=0;
# restart

View File

@@ -0,0 +1,19 @@
--source include/have_innodb.inc
--source include/have_sequence.inc
--source include/not_embedded.inc
SET GLOBAL
innodb_file_per_table=OFF,
innodb_purge_rseg_truncate_frequency=1,
innodb_immediate_scrub_data_uncompressed=ON;
CREATE TABLE t1(f1 INT NOT NULL, f2 INT NOT NULL,
f3 INT NOT NULL, INDEX(f1),
INDEX(f2), INDEX(f3))ENGINE=InnoDB;
INSERT INTO t1 SELECT seq, seq, seq FROM seq_1_to_16384;
INSERT INTO t1 SELECT seq, seq, seq FROM seq_1_to_16384;
INSERT INTO t1 SELECT seq, seq, seq FROM seq_1_to_16384;
DROP TABLE t1;
SET GLOBAL innodb_max_purge_lag_wait=0;
# The crash recovery would occasionally fail.
let $shutdown_timeout=0;
--source include/restart_mysqld.inc

View File

@@ -2683,14 +2683,23 @@ fseg_free_extent(
not_full_n_used - descr_n_used);
}
std::vector<uint8_t> going_to_free;
static_assert(FSP_EXTENT_SIZE_MIN == 256, "compatibility");
static_assert(FSP_EXTENT_SIZE_MAX == 64, "compatibility");
for (uint32_t i = 0; i < FSP_EXTENT_SIZE; i++) {
if (!xdes_is_free(descr, i)) {
buf_page_free(space, first_page_in_extent + i, mtr,
__FILE__, __LINE__);
going_to_free.emplace_back(uint8_t(i));
}
}
fsp_free_extent(space, page, mtr);
for (uint32_t i : going_to_free) {
mtr->free(*space, first_page_in_extent + i);
buf_page_free(space, first_page_in_extent + i, mtr,
__FILE__, __LINE__);
}
}
/**********************************************************************//**