3104 Jon Olav Hauglid 2010-08-13
Bug #54105 assert in MDL_context::release_locks_stored_before
The problem was that SHOW CREATE EVENT released all metadata locks
held by the current transaction. This made any exisiting savepoints
invalid, triggering the assert when ROLLBACK TO SAVEPOINT later
was executed.
This patch fixes the problem by making sure SHOW CREATE EVENT only
releases metadata locks acquired by the statement itself.
Test case added to event_trans.test.
modified:
mysql-test/r/events_trans.result
mysql-test/t/events_trans.test
sql/event_db_repository.cc
sql/events.cc
3103 Konstantin Osipov 2010-08-12
Remove dead code.
@ sql/sql_base.cc
Remove dead code.
@ sql/sql_base.h
Remove an unused parameter.
@ sql/sql_servers.cc
Remove an unused parameter.
modified:
sql/sql_base.cc
sql/sql_base.h
sql/sql_servers.cc
=== modified file 'mysql-test/r/events_trans.result'
--- a/mysql-test/r/events_trans.result 2007-10-26 20:40:48 +0000
+++ b/mysql-test/r/events_trans.result 2010-08-13 08:02:37 +0000
@@ -116,3 +116,22 @@ OK: create event: database does not exis
delete from t1;
commit work;
drop database events_test;
+#
+# Bug#54105 assert in MDL_context::release_locks_stored_before
+#
+USE test;
+DROP TABLE IF EXISTS t1, t2;
+DROP EVENT IF EXISTS e1;
+CREATE TABLE t1 (a INT) ENGINE=InnoDB;
+CREATE TABLE t2 (a INT);
+CREATE EVENT e1 ON SCHEDULE EVERY 1 DAY DO SELECT 1;
+START TRANSACTION;
+INSERT INTO t1 VALUES (1);
+SAVEPOINT A;
+SHOW CREATE EVENT e1;
+Event sql_mode time_zone Create Event character_set_client collation_connection Database Collation
+e1 SYSTEM CREATE DEFINER=`root`@`localhost` EVENT `e1` ON SCHEDULE EVERY 1 DAY STARTS '#' ON COMPLETION NOT PRESERVE ENABLE DO SELECT 1 latin1 latin1_swedish_ci latin1_swedish_ci
+SELECT * FROM t2;
+a
+ROLLBACK WORK TO SAVEPOINT A;
+DROP TABLE t1, t2;
=== modified file 'mysql-test/t/events_trans.test'
--- a/mysql-test/t/events_trans.test 2008-05-09 07:43:02 +0000
+++ b/mysql-test/t/events_trans.test 2010-08-13 08:02:37 +0000
@@ -121,3 +121,28 @@ let $wait_condition=
drop database events_test;
+
+--echo #
+--echo # Bug#54105 assert in MDL_context::release_locks_stored_before
+--echo #
+
+USE test;
+
+--disable_warnings
+DROP TABLE IF EXISTS t1, t2;
+DROP EVENT IF EXISTS e1;
+--enable_warnings
+
+CREATE TABLE t1 (a INT) ENGINE=InnoDB;
+CREATE TABLE t2 (a INT);
+CREATE EVENT e1 ON SCHEDULE EVERY 1 DAY DO SELECT 1;
+
+START TRANSACTION;
+INSERT INTO t1 VALUES (1);
+SAVEPOINT A;
+--replace_regex /STARTS '[^']+'/STARTS '#'/
+SHOW CREATE EVENT e1;
+SELECT * FROM t2;
+ROLLBACK WORK TO SAVEPOINT A;
+
+DROP TABLE t1, t2;
=== modified file 'sql/event_db_repository.cc'
--- a/sql/event_db_repository.cc 2010-07-27 10:25:53 +0000
+++ b/sql/event_db_repository.cc 2010-08-13 08:02:37 +0000
@@ -996,24 +996,33 @@ Event_db_repository::load_named_event(TH
LEX_STRING name, Event_basic *etn)
{
bool ret;
- TABLE *table= NULL;
ulong saved_mode= thd->variables.sql_mode;
+ Open_tables_backup open_tables_backup;
+ TABLE_LIST event_table;
DBUG_ENTER("Event_db_repository::load_named_event");
DBUG_PRINT("enter",("thd: 0x%lx name: %*s", (long) thd,
(int) name.length, name.str));
+ event_table.init_one_table("mysql", 5, "event", 5, "event", TL_READ);
+
/* Reset sql_mode during data dictionary operations. */
thd->variables.sql_mode= 0;
- if (!(ret= open_event_table(thd, TL_READ, &table)))
+ /*
+ We don't use open_event_table() here to make sure that SHOW
+ CREATE EVENT works properly in transactional context, and
+ does not release transactional metadata locks when the
+ event table is closed.
+ */
+ if (!(ret= open_system_tables_for_read(thd, &event_table, &open_tables_backup)))
{
- if ((ret= find_named_event(dbname, name, table)))
+ if ((ret= find_named_event(dbname, name, event_table.table)))
my_error(ER_EVENT_DOES_NOT_EXIST, MYF(0), name.str);
- else if ((ret= etn->load_from_row(thd, table)))
+ else if ((ret= etn->load_from_row(thd, event_table.table)))
my_error(ER_CANNOT_LOAD_FROM_TABLE, MYF(0), "event");
- close_mysql_tables(thd);
+ close_system_tables(thd, &open_tables_backup);
}
thd->variables.sql_mode= saved_mode;
=== modified file 'sql/events.cc'
--- a/sql/events.cc 2010-07-27 10:25:53 +0000
+++ b/sql/events.cc 2010-08-13 08:02:37 +0000
@@ -699,7 +699,6 @@ send_show_create_event(THD *thd, Event_t
bool
Events::show_create_event(THD *thd, LEX_STRING dbname, LEX_STRING name)
{
- Open_tables_backup open_tables_backup;
Event_timed et;
bool ret;
@@ -722,9 +721,7 @@ Events::show_create_event(THD *thd, LEX_
deadlock can occur please refer to the description of 'system table'
flag.
*/
- thd->reset_n_backup_open_tables_state(&open_tables_backup);
ret= db_repository->load_named_event(thd, dbname, name, &et);
- thd->restore_backup_open_tables_state(&open_tables_backup);
if (!ret)
ret= send_show_create_event(thd, &et, thd->protocol);
Attachment: [text/bzr-bundle] bzr/jon.hauglid@oracle.com-20100813080237-1b1kez10r2t05cbh.bundle
| Thread |
|---|
| • bzr push into mysql-5.5-bugfixing branch (jon.hauglid:3103 to 3104) Bug#54105 | Jon Olav Hauglid | 13 Aug |