2710 Tomas Ulin 2008-10-29
Bug#40246 - alter when table is locked does not work
added:
mysql-test/suite/ndb/r/ndb_dbug_lock.result
mysql-test/suite/ndb/t/ndb_dbug_lock.test
modified:
sql/ha_ndbcluster.cc
sql/ha_ndbcluster_binlog.cc
sql/ha_ndbcluster_binlog.h
sql/handler.cc
sql/handler.h
sql/sql_table.cc
2709 Tomas Ulin 2008-10-28 [merge]
merge
modified:
storage/ndb/src/cw/cpcd/main.cpp
2708 Tomas Ulin 2008-10-28 [merge]
merge
removed:
extra/yassl/taocrypt/taocrypt.vcproj
extra/yassl/yassl.vcproj
include/mysql_h.ic
mysql-test/suite/funcs_1/r/memory_storedproc.result
mysql-test/suite/funcs_1/r/myisam_storedproc.result
mysql-test/suite/funcs_1/r/ndb_storedproc.result
mysql-test/suite/funcs_1/t/innodb_storedproc.test
mysql-test/suite/funcs_1/t/memory_storedproc.test
mysql-test/suite/funcs_1/t/myisam_storedproc.test
mysql-test/suite/parts/t/partition_alter2_ndb.test
mysql-test/suite/rpl/t/rpl_view-slave.opt
server-tools/instance-manager/mysqlmanager.vcproj
added:
include/mysql.h.pp
include/mysql/plugin.h.pp
mysql-test/extra/rpl_tests/rpl_blackhole.test
mysql-test/r/skip_log_bin.result
mysql-test/suite/binlog/r/binlog_grant.result
mysql-test/suite/binlog/r/binlog_mix_innodb_stat.result
mysql-test/suite/binlog/r/binlog_stm_row.result
mysql-test/suite/binlog/t/binlog_grant.test
mysql-test/suite/binlog/t/binlog_mix_innodb_stat.test
mysql-test/suite/binlog/t/binlog_stm_row.test
mysql-test/suite/funcs_1/storedproc/param_check.inc
mysql-test/suite/parts/inc/partition_alter2_2.inc
mysql-test/suite/parts/inc/partition_auto_increment.inc
mysql-test/suite/parts/r/partition_alter2_2_innodb.result
mysql-test/suite/parts/r/partition_alter2_2_myisam.result
mysql-test/suite/parts/r/partition_auto_increment_archive.result
mysql-test/suite/parts/r/partition_auto_increment_blackhole.result
mysql-test/suite/parts/r/partition_auto_increment_innodb.result
mysql-test/suite/parts/r/partition_auto_increment_memory.result
mysql-test/suite/parts/r/partition_auto_increment_myisam.result
mysql-test/suite/parts/r/partition_auto_increment_ndb.result
mysql-test/suite/parts/t/partition_alter2_2_innodb.test
mysql-test/suite/parts/t/partition_alter2_2_myisam.test
mysql-test/suite/parts/t/partition_auto_increment_archive.test
mysql-test/suite/parts/t/partition_auto_increment_blackhole.test
mysql-test/suite/parts/t/partition_auto_increment_innodb.test
mysql-test/suite/parts/t/partition_auto_increment_memory.test
mysql-test/suite/parts/t/partition_auto_increment_myisam.test
mysql-test/suite/parts/t/partition_auto_increment_ndb.test
mysql-test/suite/rpl/r/rpl_binlog_query_filter_rules.result
mysql-test/suite/rpl/r/rpl_blackhole.result
mysql-test/suite/rpl/t/rpl_binlog_query_filter_rules-master.opt
mysql-test/suite/rpl/t/rpl_binlog_query_filter_rules.test
mysql-test/suite/rpl/t/rpl_blackhole.test
mysql-test/t/skip_log_bin-master.opt
mysql-test/t/skip_log_bin.test
sql/mysql_priv.h.pp
win/build-vs9.bat
win/build-vs9_x64.bat
renamed:
mysql-test/suite/funcs_1/r/innodb_storedproc.result => mysql-test/suite/funcs_1/r/storedproc.result
mysql-test/suite/funcs_1/storedproc/storedproc_master.inc => mysql-test/suite/funcs_1/t/storedproc.test
mysql-test/suite/parts/inc/partition_alter2.inc => mysql-test/suite/parts/inc/partition_alter2_1.inc
mysql-test/suite/parts/r/partition_alter2_innodb.result => mysql-test/suite/parts/r/partition_alter2_1_innodb.result
mysql-test/suite/parts/r/partition_alter2_myisam.result => mysql-test/suite/parts/r/partition_alter2_1_myisam.result
mysql-test/suite/parts/t/partition_alter2_innodb.test => mysql-test/suite/parts/t/partition_alter2_1_innodb.test
mysql-test/suite/parts/t/partition_alter2_myisam.test => mysql-test/suite/parts/t/partition_alter2_1_myisam.test
mysql-test/suite/rpl/r/rpl_truncate_7ndb_2.result => mysql-test/suite/rpl_ndb/r/rpl_truncate_7ndb_2.result
mysql-test/suite/rpl/t/rpl_truncate_7ndb_2-master.opt => mysql-test/suite/rpl_ndb/t/rpl_truncate_7ndb_2-master.opt
mysql-test/suite/rpl/t/rpl_truncate_7ndb_2.test => mysql-test/suite/rpl_ndb/t/rpl_truncate_7ndb_2.test
modified:
BUILD/compile-dist
BUILD/compile-solaris-amd64-forte*
BUILD/compile-solaris-amd64-forte-debug
BUILD/compile-solaris-sparc
BUILD/compile-solaris-sparc-forte
CMakeLists.txt
Makefile.am
client/mysqldump.c
configure.in
extra/Makefile.am
extra/yassl/Makefile.am
extra/yassl/taocrypt/Makefile.am
include/Makefile.am
include/hash.h
include/thr_lock.h
libmysql/dll.c
man/Makefile.am
mysql-test/extra/binlog_tests/binlog.test
mysql-test/extra/binlog_tests/blackhole.test
mysql-test/extra/binlog_tests/innodb_stat.test
mysql-test/extra/rpl_tests/rpl_EE_err.test
mysql-test/extra/rpl_tests/rpl_ddl.test
mysql-test/extra/rpl_tests/rpl_log.test
mysql-test/extra/rpl_tests/rpl_row_basic.test
mysql-test/include/grant_cache.inc
mysql-test/include/index_merge1.inc
mysql-test/include/mix1.inc
mysql-test/include/ndb_backup_print.inc
mysql-test/lib/mtr_cases.pl
mysql-test/lib/mtr_report.pl
mysql-test/mysql-test-run.pl
mysql-test/r/auto_increment.result
mysql-test/r/compare.result
mysql-test/r/create.result
mysql-test/r/ctype_cp932_binlog_stm.result
mysql-test/r/ctype_ucs.result
mysql-test/r/default.result
mysql-test/r/distinct.result
mysql-test/r/events_2.result
mysql-test/r/federated.result
mysql-test/r/federated_bug_25714.result
mysql-test/r/func_group.result
mysql-test/r/func_regexp.result
mysql-test/r/grant2.result
mysql-test/r/grant_cache_no_prot.result
mysql-test/r/grant_cache_ps_prot.result
mysql-test/r/index_merge_myisam.result
mysql-test/r/information_schema_db.result
mysql-test/r/innodb-semi-consistent.result
mysql-test/r/innodb.result
mysql-test/r/innodb_mysql.result
mysql-test/r/join.result
mysql-test/r/loaddata.result
mysql-test/r/lock_multi.result
mysql-test/r/log_basic.result
mysql-test/r/log_bin_trust_routine_creators_basic.result
mysql-test/r/log_state.result
mysql-test/r/log_tables.result
mysql-test/r/mysqldump-max.result
mysql-test/r/mysqldump.result
mysql-test/r/partition.result
mysql-test/r/partition_range.result
mysql-test/r/slow_launch_time_func.result
mysql-test/r/sp-error.result
mysql-test/r/sp.result
mysql-test/r/status.result
mysql-test/r/trigger-trans.result
mysql-test/r/tx_isolation_func.result
mysql-test/r/type_datetime.result
mysql-test/r/type_set.result
mysql-test/r/user_var.result
mysql-test/r/view_grant.result
mysql-test/r/warnings.result
mysql-test/suite/binlog/r/binlog_multi_engine.result
mysql-test/suite/binlog/r/binlog_row_binlog.result
mysql-test/suite/binlog/r/binlog_row_innodb_stat.result
mysql-test/suite/binlog/r/binlog_stm_binlog.result
mysql-test/suite/binlog/r/binlog_stm_blackhole.result
mysql-test/suite/binlog/r/binlog_stm_innodb_stat.result
mysql-test/suite/binlog/t/binlog_killed.test
mysql-test/suite/binlog/t/binlog_killed_simulate.test
mysql-test/suite/binlog/t/binlog_multi_engine.test
mysql-test/suite/binlog/t/binlog_start_comment.test
mysql-test/suite/binlog/t/binlog_stm_innodb_stat.test
mysql-test/suite/funcs_1/datadict/processlist_priv.inc
mysql-test/suite/funcs_1/r/processlist_priv_no_prot.result
mysql-test/suite/funcs_1/r/processlist_priv_ps.result
mysql-test/suite/funcs_1/views/func_view.inc
mysql-test/suite/ndb/t/ndb_restore_print.test
mysql-test/suite/ndb_team/t/ndb_autodiscover.test
mysql-test/suite/parts/t/disabled.def
mysql-test/suite/rpl/r/rpl_row_basic_2myisam.result
mysql-test/suite/rpl/r/rpl_row_basic_3innodb.result
mysql-test/suite/rpl/r/rpl_row_create_table.result
mysql-test/suite/rpl/r/rpl_row_log.result
mysql-test/suite/rpl/r/rpl_row_log_innodb.result
mysql-test/suite/rpl/r/rpl_sp.result
mysql-test/suite/rpl/r/rpl_stm_log.result
mysql-test/suite/rpl/r/rpl_temporary.result
mysql-test/suite/rpl/t/disabled.def
mysql-test/suite/rpl/t/rpl_row_create_table.test
mysql-test/suite/rpl/t/rpl_stm_log-slave.opt
mysql-test/suite/rpl/t/rpl_temporary.test
mysql-test/suite/rpl_ndb/r/rpl_row_basic_7ndb.result
mysql-test/t/auto_increment.test
mysql-test/t/compare.test
mysql-test/t/create.test
mysql-test/t/ctype_big5.test
mysql-test/t/ctype_ucs.test
mysql-test/t/default.test
mysql-test/t/disabled.def
mysql-test/t/distinct.test
mysql-test/t/events_2.test
mysql-test/t/federated.test
mysql-test/t/federated_bug_25714.test
mysql-test/t/func_group.test
mysql-test/t/func_regexp.test
mysql-test/t/grant2.test
mysql-test/t/information_schema_db.test
mysql-test/t/innodb-semi-consistent.test
mysql-test/t/innodb.test
mysql-test/t/join.test
mysql-test/t/loaddata.test
mysql-test/t/lock_multi.test
mysql-test/t/log_basic.test
mysql-test/t/log_state.test
mysql-test/t/log_tables.test
mysql-test/t/mysqldump-max.test
mysql-test/t/mysqldump.test
mysql-test/t/outfile.test
mysql-test/t/partition.test
mysql-test/t/partition_range.test
mysql-test/t/slow_launch_time_func.test
mysql-test/t/sp-error.test
mysql-test/t/sp.test
mysql-test/t/status.test
mysql-test/t/symlink.test
mysql-test/t/trigger-trans.test
mysql-test/t/tx_isolation_func.test
mysql-test/t/type_datetime.test
mysql-test/t/type_set.test
mysql-test/t/user_var.test
mysql-test/t/view_grant.test
mysys/hash.c
mysys/stacktrace.c
scripts/make_binary_distribution.sh
scripts/mysql_system_tables_data.sql
sql/event_db_repository.cc
sql/event_parse_data.cc
sql/event_parse_data.h
sql/field.cc
sql/field.h
sql/ha_partition.cc
sql/ha_partition.h
sql/handler.cc
sql/handler.h
sql/item.cc
sql/item.h
sql/item_cmpfunc.cc
sql/item_cmpfunc.h
sql/item_func.cc
sql/item_func.h
sql/lock.cc
sql/log.cc
sql/log.h
sql/log_event.cc
sql/mysql_priv.h
sql/mysqld.cc
sql/opt_range.cc
sql/parse_file.cc
sql/parse_file.h
sql/partition_info.h
sql/set_var.cc
sql/set_var.h
sql/sp_head.cc
sql/sql_acl.cc
sql/sql_base.cc
sql/sql_cache.cc
sql/sql_class.cc
sql/sql_class.h
sql/sql_db.cc
sql/sql_derived.cc
sql/sql_insert.cc
sql/sql_lex.cc
sql/sql_lex.h
sql/sql_load.cc
sql/sql_parse.cc
sql/sql_partition.cc
sql/sql_select.cc
sql/sql_show.cc
sql/sql_show.h
sql/sql_table.cc
sql/sql_union.cc
sql/sql_update.cc
sql/sql_view.cc
sql/sql_yacc.yy
sql/table.cc
sql/table.h
storage/blackhole/ha_blackhole.cc
storage/blackhole/ha_blackhole.h
support-files/my-huge.cnf.sh
support-files/my-innodb-heavy-4G.cnf.sh
support-files/my-large.cnf.sh
support-files/my-medium.cnf.sh
support-files/my-small.cnf.sh
support-files/mysql.spec.sh
win/create_manifest.js
zlib/gzio.c
zlib/zutil.h
mysql-test/suite/funcs_1/r/storedproc.result
mysql-test/suite/funcs_1/t/storedproc.test
mysql-test/suite/parts/inc/partition_alter2_1.inc
mysql-test/suite/parts/r/partition_alter2_1_innodb.result
mysql-test/suite/parts/r/partition_alter2_1_myisam.result
mysql-test/suite/parts/t/partition_alter2_1_innodb.test
mysql-test/suite/parts/t/partition_alter2_1_myisam.test
mysql-test/suite/rpl_ndb/r/rpl_truncate_7ndb_2.result
mysql-test/suite/rpl_ndb/t/rpl_truncate_7ndb_2.test
=== added file 'mysql-test/suite/ndb/r/ndb_dbug_lock.result'
--- a/mysql-test/suite/ndb/r/ndb_dbug_lock.result 1970-01-01 00:00:00 +0000
+++ b/mysql-test/suite/ndb/r/ndb_dbug_lock.result 2008-10-29 13:09:15 +0000
@@ -0,0 +1,44 @@
+drop table if exists t1;
+#
+# Test that alter during lock table aborts with error if
+# global schema lock already exists
+#
+create table t1 (a int key) engine ndb row_format dynamic;
+set session debug="+d,sleep_after_global_schema_lock";
+alter table t1 add column (b int);
+lock tables t1 write;
+alter table t1 add column (c int);
+ERROR HY000: Can't execute the given command because you have active locked tables or an active transaction
+alter table t1 add column (c int);
+ERROR HY000: Can't execute the given command because you have active locked tables or an active transaction
+alter table t1 add column (c int);
+ERROR HY000: Can't execute the given command because you have active locked tables or an active transaction
+unlock tables;
+#
+# Test that alter during lock works without global schema lock
+# and that an alter done in parallell test serialized
+#
+lock tables t1 write;
+# delay is still set after lock
+alter table t1 add column (c int);
+# issue alter in parallell, which should be hanging waiting on
+alter table t1 add column (d int);
+# check thread state which should be:
+# "Waiting for allowed to take ndbcluster global schema lock"
+# _not_ "Waiting for ndbcluster global schema lock"
+select state from information_schema.processlist where info = "alter table t1 add column (d int)";
+state
+Waiting for allowed to take ndbcluster global schema lock
+unlock tables;
+show create table t1;
+Table Create Table
+t1 CREATE TABLE `t1` (
+ `a` int(11) NOT NULL,
+ `b` int(11) DEFAULT NULL,
+ `c` int(11) DEFAULT NULL,
+ `d` int(11) DEFAULT NULL,
+ PRIMARY KEY (`a`)
+) ENGINE=ndbcluster DEFAULT CHARSET=latin1 ROW_FORMAT=DYNAMIC
+# Cleanup
+set session debug="-d,sleep_after_global_schema_lock";
+drop table t1;
=== added file 'mysql-test/suite/ndb/t/ndb_dbug_lock.test'
--- a/mysql-test/suite/ndb/t/ndb_dbug_lock.test 1970-01-01 00:00:00 +0000
+++ b/mysql-test/suite/ndb/t/ndb_dbug_lock.test 2008-10-29 13:09:15 +0000
@@ -0,0 +1,70 @@
+-- source include/have_ndb.inc
+# We are using some debug-only features in this test
+--source include/have_debug.inc
+
+--disable_warnings
+drop table if exists t1;
+--enable_warnings
+
+--connect (another_con, localhost, root,,)
+--connect (yet_another_con, localhost, root,,)
+
+--echo #
+--echo # Test that alter during lock table aborts with error if
+--echo # global schema lock already exists
+--echo #
+--connection default
+create table t1 (a int key) engine ndb row_format dynamic;
+# delay after lock
+set session debug="+d,sleep_after_global_schema_lock";
+--send alter table t1 add column (b int)
+--sleep 2
+
+--connection another_con
+lock tables t1 write;
+--error ER_LOCK_OR_ACTIVE_TRANSACTION
+alter table t1 add column (c int);
+# make sure it continues to block
+--error ER_LOCK_OR_ACTIVE_TRANSACTION
+alter table t1 add column (c int);
+--error ER_LOCK_OR_ACTIVE_TRANSACTION
+alter table t1 add column (c int);
+unlock tables;
+
+--connection default
+--reap
+
+--echo #
+--echo # Test that alter during lock works without global schema lock
+--echo # and that an alter done in parallell test serialized
+--echo #
+--connection default
+lock tables t1 write;
+--echo # delay is still set after lock
+--send alter table t1 add column (c int)
+--sleep 2
+
+--echo # issue alter in parallell, which should be hanging waiting on
+--connection another_con
+--send alter table t1 add column (d int)
+
+--echo # check thread state which should be:
+--echo # "Waiting for allowed to take ndbcluster global schema lock"
+--echo # _not_ "Waiting for ndbcluster global schema lock"
+--connection yet_another_con
+select state from information_schema.processlist where info = "alter table t1 add column (d int)";
+
+# wait for alter to complete
+--connection default
+--reap
+unlock tables;
+
+--connection another_con
+--reap
+
+show create table t1;
+
+--echo # Cleanup
+--connection default
+set session debug="-d,sleep_after_global_schema_lock";
+drop table t1;
=== modified file 'sql/ha_ndbcluster.cc'
--- a/sql/ha_ndbcluster.cc 2008-10-28 14:02:09 +0000
+++ b/sql/ha_ndbcluster.cc 2008-10-29 13:09:15 +0000
@@ -7615,6 +7615,7 @@ static int ndbcluster_init(void *p)
ndbcluster_terminating= 0;
ndb_dictionary_is_mysqld= 1;
ndbcluster_hton= (handlerton *)p;
+ ndbcluster_global_schema_lock_init();
{
handlerton *h= ndbcluster_hton;
@@ -7667,6 +7668,7 @@ static int ndbcluster_init(void *p)
pthread_mutex_destroy(&LOCK_ndb_util_thread);
pthread_cond_destroy(&COND_ndb_util_thread);
pthread_cond_destroy(&COND_ndb_util_ready);
+ ndbcluster_global_schema_lock_deinit();
goto ndbcluster_init_error;
}
@@ -7684,6 +7686,7 @@ static int ndbcluster_init(void *p)
pthread_mutex_destroy(&LOCK_ndb_util_thread);
pthread_cond_destroy(&COND_ndb_util_thread);
pthread_cond_destroy(&COND_ndb_util_ready);
+ ndbcluster_global_schema_lock_deinit();
goto ndbcluster_init_error;
}
@@ -7747,6 +7750,7 @@ static int ndbcluster_end(handlerton *ht
pthread_mutex_destroy(&LOCK_ndb_util_thread);
pthread_cond_destroy(&COND_ndb_util_thread);
pthread_cond_destroy(&COND_ndb_util_ready);
+ ndbcluster_global_schema_lock_deinit();
DBUG_RETURN(0);
}
=== modified file 'sql/ha_ndbcluster_binlog.cc'
--- a/sql/ha_ndbcluster_binlog.cc 2008-10-09 09:10:50 +0000
+++ b/sql/ha_ndbcluster_binlog.cc 2008-10-29 13:09:15 +0000
@@ -767,7 +767,19 @@ int ndbcluster_no_global_schema_lock_abo
lock/unlock calls are reference counted, so calls to lock
must be matched to a call to unlock even if the lock call fails
*/
-static int ndbcluster_global_schema_lock(THD *thd,
+static int ndbcluster_global_schema_lock_is_locked_or_queued= 0;
+static int ndbcluster_global_schema_lock_no_locking_allowed= 0;
+static pthread_mutex_t ndbcluster_global_schema_lock_mutex;
+void ndbcluster_global_schema_lock_init()
+{
+ pthread_mutex_init(&ndbcluster_global_schema_lock_mutex, MY_MUTEX_INIT_FAST);
+}
+void ndbcluster_global_schema_lock_deinit()
+{
+ pthread_mutex_destroy(&ndbcluster_global_schema_lock_mutex);
+}
+
+static int ndbcluster_global_schema_lock(THD *thd, int no_lock_queue,
int report_cluster_disconnected)
{
Ndb *ndb= check_ndb_in_thd(thd);
@@ -776,7 +788,8 @@ static int ndbcluster_global_schema_lock
if (thd_ndb->options & TNO_NO_LOCK_SCHEMA_OP)
return 0;
DBUG_ENTER("ndbcluster_global_schema_lock");
- DBUG_PRINT("enter", ("query: %s", thd->query));
+ DBUG_PRINT("enter", ("query: %s, no_lock_queue: %d",
+ thd->query, no_lock_queue));
if (thd_ndb->global_schema_lock_count)
{
if (thd_ndb->global_schema_lock_trans)
@@ -794,8 +807,65 @@ static int ndbcluster_global_schema_lock
DBUG_PRINT("exit", ("global_schema_lock_count: %d",
thd_ndb->global_schema_lock_count));
- if ((thd_ndb->global_schema_lock_trans=
- ndbcluster_global_schema_lock_ext(thd, ndb, ndb_error, -1)) != NULL)
+ /*
+ Check that taking the lock is allowed
+ - if not allowed to enter lock queue, return if lock exists
+ - wait until allowed
+ - increase global lock count
+ */
+ Thd_proc_info_guard thd_proc_info_guard(thd);
+ pthread_mutex_lock(&ndbcluster_global_schema_lock_mutex);
+ /* increase global lock count */
+ ndbcluster_global_schema_lock_is_locked_or_queued++;
+ if (no_lock_queue)
+ {
+ if (ndbcluster_global_schema_lock_is_locked_or_queued != 1)
+ {
+ /* Other thread has lock and this thread may not enter lock queue */
+ pthread_mutex_unlock(&ndbcluster_global_schema_lock_mutex);
+ thd_ndb->global_schema_lock_error= -1;
+ DBUG_PRINT("exit", ("aborting as lock exists"));
+ DBUG_RETURN(-1);
+ }
+ /* Mark that no other thread may be take lock */
+ ndbcluster_global_schema_lock_no_locking_allowed= 1;
+ }
+ else
+ {
+ while (ndbcluster_global_schema_lock_no_locking_allowed)
+ {
+ thd_proc_info(thd, "Waiting for allowed to take ndbcluster global schema lock");
+ /* Wait until locking is allowed */
+ pthread_mutex_unlock(&ndbcluster_global_schema_lock_mutex);
+ do_retry_sleep(50);
+ if (thd->killed)
+ {
+ thd_ndb->global_schema_lock_error= -1;
+ DBUG_RETURN(-1);
+ }
+ pthread_mutex_lock(&ndbcluster_global_schema_lock_mutex);
+ }
+ }
+ pthread_mutex_unlock(&ndbcluster_global_schema_lock_mutex);
+
+ /*
+ Take the lock
+ */
+ thd_proc_info(thd, "Waiting for ndbcluster global schema lock");
+ thd_ndb->global_schema_lock_trans=
+ ndbcluster_global_schema_lock_ext(thd, ndb, ndb_error, -1);
+
+ DBUG_EXECUTE_IF("sleep_after_global_schema_lock", my_sleep(6000000););
+
+ if (no_lock_queue)
+ {
+ pthread_mutex_lock(&ndbcluster_global_schema_lock_mutex);
+ /* Mark that other thread may be take lock */
+ ndbcluster_global_schema_lock_no_locking_allowed= 0;
+ pthread_mutex_unlock(&ndbcluster_global_schema_lock_mutex);
+ }
+
+ if (thd_ndb->global_schema_lock_trans)
{
DBUG_RETURN(0);
}
@@ -838,6 +908,14 @@ static int ndbcluster_global_schema_unlo
DBUG_RETURN(0);
}
thd_ndb->global_schema_lock_error= 0;
+
+ /*
+ Decrease global lock count
+ */
+ pthread_mutex_lock(&ndbcluster_global_schema_lock_mutex);
+ ndbcluster_global_schema_lock_is_locked_or_queued--;
+ pthread_mutex_unlock(&ndbcluster_global_schema_lock_mutex);
+
if (trans)
{
thd_ndb->global_schema_lock_trans= NULL;
@@ -879,7 +957,7 @@ static int ndbcluster_binlog_func(handle
ndbcluster_binlog_index_purge_file(thd, (const char *)arg);
break;
case BFN_GLOBAL_SCHEMA_LOCK:
- DBUG_RETURN(ndbcluster_global_schema_lock(thd, 1));
+ DBUG_RETURN(ndbcluster_global_schema_lock(thd, *(int*)arg, 1));
break;
case BFN_GLOBAL_SCHEMA_UNLOCK:
ndbcluster_global_schema_unlock(thd);
@@ -906,7 +984,7 @@ int Ndbcluster_global_schema_lock_guard:
of calls to lock and unlock need to match up.
*/
m_lock= 1;
- return ndbcluster_global_schema_lock(m_thd, 0);
+ return ndbcluster_global_schema_lock(m_thd, 0, 0);
}
void ndbcluster_binlog_init_handlerton()
=== modified file 'sql/ha_ndbcluster_binlog.h'
--- a/sql/ha_ndbcluster_binlog.h 2008-10-07 08:19:31 +0000
+++ b/sql/ha_ndbcluster_binlog.h 2008-10-29 13:09:15 +0000
@@ -135,7 +135,20 @@ private:
int m_invalidate;
};
+class Thd_proc_info_guard
+{
+public:
+ Thd_proc_info_guard(THD *thd)
+ : m_thd(thd), m_proc_info(thd->proc_info) {}
+ ~Thd_proc_info_guard() { m_thd->proc_info= m_proc_info; }
+private:
+ THD *m_thd;
+ const char *m_proc_info;
+};
+
extern Ndb_cluster_connection* g_ndb_cluster_connection;
+void ndbcluster_global_schema_lock_init();
+void ndbcluster_global_schema_lock_deinit();
#ifdef HAVE_NDB_BINLOG
extern pthread_t ndb_binlog_thread;
=== modified file 'sql/handler.cc'
--- a/sql/handler.cc 2008-10-28 14:02:09 +0000
+++ b/sql/handler.cc 2008-10-29 13:09:15 +0000
@@ -3891,14 +3891,15 @@ static my_bool binlog_func_foreach(THD *
{
hton_list_st hton_list;
uint i, sz;
+ int res= 0;
hton_list.sz= 0;
plugin_foreach(thd, binlog_func_list,
MYSQL_STORAGE_ENGINE_PLUGIN, &hton_list);
for (i= 0, sz= hton_list.sz; i < sz ; i++)
- hton_list.hton[i]->binlog_func(hton_list.hton[i], thd, bfn->fn, bfn->arg);
- return FALSE;
+ res|= hton_list.hton[i]->binlog_func(hton_list.hton[i], thd, bfn->fn, bfn->arg);
+ return res != 0;
}
int ha_reset_logs(THD *thd)
@@ -3941,11 +3942,11 @@ int ha_binlog_index_purge_file(THD *thd,
return 0;
}
-static int ha_global_schema_lock(THD *thd)
+static int ha_global_schema_lock(THD *thd, int no_queue)
{
- binlog_func_st bfn= {BFN_GLOBAL_SCHEMA_LOCK, 0};
- binlog_func_foreach(thd, &bfn);
- if (thd->main_da.is_error())
+ binlog_func_st bfn= {BFN_GLOBAL_SCHEMA_LOCK, (void *)&no_queue};
+ int res= binlog_func_foreach(thd, &bfn);
+ if (res || thd->main_da.is_error())
return 1;
return 0;
}
@@ -3970,11 +3971,11 @@ Ha_global_schema_lock_guard::~Ha_global_
ha_global_schema_unlock(m_thd);
}
-int Ha_global_schema_lock_guard::lock()
+int Ha_global_schema_lock_guard::lock(int no_queue)
{
DBUG_ASSERT(m_lock == 0);
m_lock= 1;
- return ha_global_schema_lock(m_thd);
+ return ha_global_schema_lock(m_thd, no_queue);
}
struct binlog_log_query_st
=== modified file 'sql/handler.h'
--- a/sql/handler.h 2008-10-28 14:02:09 +0000
+++ b/sql/handler.h 2008-10-29 13:09:15 +0000
@@ -2198,7 +2198,7 @@ class Ha_global_schema_lock_guard
public:
Ha_global_schema_lock_guard(THD *thd);
~Ha_global_schema_lock_guard();
- int lock();
+ int lock(int no_queue= 0);
private:
THD *m_thd;
int m_lock;
@@ -2216,6 +2216,6 @@ class Ha_global_schema_lock_guard
public:
Ha_global_schema_lock_guard(THD *thd) {}
~Ha_global_schema_lock_guard() {}
- int lock() { return 0; }
+ int lock(int no_queue= 0) { return 0; }
};
#endif
=== modified file 'sql/sql_table.cc'
--- a/sql/sql_table.cc 2008-10-28 14:02:09 +0000
+++ b/sql/sql_table.cc 2008-10-29 13:09:15 +0000
@@ -6639,16 +6639,24 @@ view_err:
if (table_type == DB_TYPE_NDBCLUSTER ||
(create_info->db_type && create_info->db_type->db_type == DB_TYPE_NDBCLUSTER))
{
- /*
- To avoid deadlock in this situation
- */
if (thd->locked_tables)
{
- my_message(ER_LOCK_OR_ACTIVE_TRANSACTION,
- ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
- DBUG_RETURN(TRUE);
+ /*
+ To avoid deadlock in this situation:
+ - if other thread has lock do not enter lock queue
+ and report an error instead
+ */
+ if (global_schema_lock_guard.lock(1))
+ {
+ my_message(ER_LOCK_OR_ACTIVE_TRANSACTION,
+ ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
+ DBUG_RETURN(TRUE);
+ }
+ }
+ else
+ {
+ global_schema_lock_guard.lock();
}
- global_schema_lock_guard.lock();
}
if (!(table= open_n_lock_single_table(thd, table_list, TL_WRITE_ALLOW_READ)))
DBUG_RETURN(TRUE);
=== modified file 'storage/ndb/src/cw/cpcd/main.cpp'
--- a/storage/ndb/src/cw/cpcd/main.cpp 2007-05-10 09:59:39 +0000
+++ b/storage/ndb/src/cw/cpcd/main.cpp 2008-10-28 15:16:07 +0000
@@ -75,7 +75,7 @@ const char *progname = "ndb_cpcd";
int main(int argc, char** argv){
const char *load_default_groups[]= { "ndb_cpcd",0 };
- MY_INIT(argv[0]);
+ NDB_INIT(argv[0]);
load_defaults("ndb_cpcd",load_default_groups,&argc,&argv);
if (handle_options(&argc, &argv, my_long_options, get_one_option)) {
| Thread |
|---|
| • bzr push into mysql-5.1 branch (tomas.ulin:2708 to 2710) Bug#40246 | Tomas Ulin | 29 Oct |