summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarko Mäkelä <marko.makela@mariadb.com>2020-12-01 15:24:49 +0200
committerMarko Mäkelä <marko.makela@mariadb.com>2020-12-01 15:24:49 +0200
commit73f34336e33e979942a6eb38bdbc7d34ff092d85 (patch)
tree081e62326b247eace36eec0206a30a6aa3c366ea
parent81ab9ea63f5d3ad4909bb75552008d6b035a371b (diff)
downloadmariadb-git-73f34336e33e979942a6eb38bdbc7d34ff092d85.tar.gz
MDEV-24323 Crash on recovery after kill during instant ADD COLUMN
row_undo_ins_parse_undo_rec(): Do not try to read non-existing virtual column information for the metadata record.
-rw-r--r--mysql-test/suite/innodb/r/instant_alter_crash.result29
-rw-r--r--mysql-test/suite/innodb/t/instant_alter_crash.test28
-rw-r--r--storage/innobase/row/row0uins.cc7
3 files changed, 57 insertions, 7 deletions
diff --git a/mysql-test/suite/innodb/r/instant_alter_crash.result b/mysql-test/suite/innodb/r/instant_alter_crash.result
index f54b88be0e4..f2a06882c3c 100644
--- a/mysql-test/suite/innodb/r/instant_alter_crash.result
+++ b/mysql-test/suite/innodb/r/instant_alter_crash.result
@@ -42,7 +42,6 @@ SET debug_dbug='+d,dict_sys_mutex_avoid';
DELETE FROM t1;
# Kill the server
disconnect ddl;
-SET @saved_frequency= @@GLOBAL.innodb_purge_rseg_truncate_frequency;
SET GLOBAL innodb_purge_rseg_truncate_frequency=1;
FOUND 2 /\[Note\] InnoDB: Rolled back recovered transaction / in mysqld.1.err
SELECT * FROM t1;
@@ -93,6 +92,22 @@ header=0x060008030000 (id=0x73757072656d756d00)
UNLOCK TABLES;
DELETE FROM t2;
InnoDB 0 transactions not purged
+#
+# MDEV-24323 Crash on recovery after kill during instant ADD COLUMN
+#
+connect ddl, localhost, root;
+CREATE TABLE t3(id INT PRIMARY KEY, c2 INT, v2 INT AS(c2) VIRTUAL, UNIQUE(v2))
+ENGINE=InnoDB;
+INSERT INTO t3 SET id=1,c2=1;
+SET DEBUG_SYNC='innodb_alter_inplace_before_commit SIGNAL ddl WAIT_FOR ever';
+ALTER TABLE t3 ADD COLUMN c3 TEXT NOT NULL DEFAULT 'sic transit gloria mundi';
+connection default;
+SET DEBUG_SYNC='now WAIT_FOR ddl';
+SET GLOBAL innodb_flush_log_at_trx_commit=1;
+SET debug_dbug='+d,dict_sys_mutex_avoid';
+INSERT INTO t1 VALUES(0,0);
+# Kill the server
+disconnect ddl;
SHOW CREATE TABLE t1;
Table Create Table
t1 CREATE TABLE `t1` (
@@ -110,6 +125,14 @@ t2 CREATE TABLE `t2` (
PRIMARY KEY (`id`),
UNIQUE KEY `c2` (`c2`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 ROW_FORMAT=REDUNDANT
-DROP TABLE t1,t2;
+SHOW CREATE TABLE t3;
+Table Create Table
+t3 CREATE TABLE `t3` (
+ `id` int(11) NOT NULL,
+ `c2` int(11) DEFAULT NULL,
+ `v2` int(11) GENERATED ALWAYS AS (`c2`) VIRTUAL,
+ PRIMARY KEY (`id`),
+ UNIQUE KEY `v2` (`v2`)
+) ENGINE=InnoDB DEFAULT CHARSET=latin1
+DROP TABLE t1,t2,t3;
db.opt
-SET GLOBAL innodb_purge_rseg_truncate_frequency=@saved_frequency;
diff --git a/mysql-test/suite/innodb/t/instant_alter_crash.test b/mysql-test/suite/innodb/t/instant_alter_crash.test
index 9edf861d2a2..c0077625102 100644
--- a/mysql-test/suite/innodb/t/instant_alter_crash.test
+++ b/mysql-test/suite/innodb/t/instant_alter_crash.test
@@ -61,7 +61,6 @@ DELETE FROM t1;
disconnect ddl;
--source include/start_mysqld.inc
-SET @saved_frequency= @@GLOBAL.innodb_purge_rseg_truncate_frequency;
SET GLOBAL innodb_purge_rseg_truncate_frequency=1;
let SEARCH_FILE= $MYSQLTEST_VARDIR/log/mysqld.1.err;
@@ -124,11 +123,32 @@ UNLOCK TABLES;
DELETE FROM t2;
--source include/wait_all_purged.inc
+--echo #
+--echo # MDEV-24323 Crash on recovery after kill during instant ADD COLUMN
+--echo #
+connect ddl, localhost, root;
+CREATE TABLE t3(id INT PRIMARY KEY, c2 INT, v2 INT AS(c2) VIRTUAL, UNIQUE(v2))
+ENGINE=InnoDB;
+INSERT INTO t3 SET id=1,c2=1;
+
+SET DEBUG_SYNC='innodb_alter_inplace_before_commit SIGNAL ddl WAIT_FOR ever';
+--send
+ALTER TABLE t3 ADD COLUMN c3 TEXT NOT NULL DEFAULT 'sic transit gloria mundi';
+
+connection default;
+SET DEBUG_SYNC='now WAIT_FOR ddl';
+SET GLOBAL innodb_flush_log_at_trx_commit=1;
+SET debug_dbug='+d,dict_sys_mutex_avoid';
+INSERT INTO t1 VALUES(0,0);
+
+--source include/kill_mysqld.inc
+disconnect ddl;
+--source include/start_mysqld.inc
+
SHOW CREATE TABLE t1;
SHOW CREATE TABLE t2;
-DROP TABLE t1,t2;
+SHOW CREATE TABLE t3;
+DROP TABLE t1,t2,t3;
--remove_files_wildcard $MYSQLD_DATADIR/test #sql*.frm
--list_files $MYSQLD_DATADIR/test
-
-SET GLOBAL innodb_purge_rseg_truncate_frequency=@saved_frequency;
diff --git a/storage/innobase/row/row0uins.cc b/storage/innobase/row/row0uins.cc
index 7da9902995c..f72ad28e70e 100644
--- a/storage/innobase/row/row0uins.cc
+++ b/storage/innobase/row/row0uins.cc
@@ -459,6 +459,13 @@ close_table:
node->heap);
} else {
node->ref = &trx_undo_metadata;
+ if (!row_undo_search_clust_to_pcur(node)) {
+ /* An error probably occurred during
+ an insert into the clustered index,
+ after we wrote the undo log record. */
+ goto close_table;
+ }
+ return;
}
if (!row_undo_search_clust_to_pcur(node)) {