diff options
-rw-r--r-- | mysql-test/r/kill.result | 14 | ||||
-rw-r--r-- | mysql-test/t/kill.test | 49 | ||||
-rw-r--r-- | sql/sql_class.cc | 3 | ||||
-rw-r--r-- | sql/sql_select.cc | 14 | ||||
-rw-r--r-- | sql/sql_select.h | 11 |
5 files changed, 87 insertions, 4 deletions
diff --git a/mysql-test/r/kill.result b/mysql-test/r/kill.result index ba9ba2833f6..828c7fcf9b0 100644 --- a/mysql-test/r/kill.result +++ b/mysql-test/r/kill.result @@ -1,4 +1,4 @@ -drop table if exists t1; +drop table if exists t1, t2, t3; create table t1 (kill_id int); insert into t1 values(connection_id()); select ((@id := kill_id) - kill_id) from t1; @@ -17,3 +17,15 @@ select 4; 4 4 drop table t1; +create table t1 (id int primary key); +create table t2 (id int unsigned not null); +insert into t2 select id from t1; +create table t3 (kill_id int); +insert into t3 values(connection_id()); + select id from t1 where id in (select distinct id from t2); +select ((@id := kill_id) - kill_id) from t3; +((@id := kill_id) - kill_id) +0 +kill @id; +ERROR 08S01: Server shutdown in progress +drop table t1, t2, t3; diff --git a/mysql-test/t/kill.test b/mysql-test/t/kill.test index aada8dd2ef3..ebe4673beb3 100644 --- a/mysql-test/t/kill.test +++ b/mysql-test/t/kill.test @@ -12,7 +12,7 @@ connect (con2, localhost, root,,); #remember id of con1 connection con1; --disable_warnings -drop table if exists t1; +drop table if exists t1, t2, t3; --enable_warnings create table t1 (kill_id int); @@ -40,4 +40,51 @@ connection con2; select 4; drop table t1; +disconnect con2; +connection default; +# +# BUG#14851: killing long running subquery processed via a temporary table. +# +create table t1 (id int primary key); +create table t2 (id int unsigned not null); + +connect (conn1, localhost, root,,); +connection conn1; + +-- disable_result_log +-- disable_query_log +let $1 = 4096; +while ($1) +{ + eval insert into t1 values ($1); + dec $1; +} +-- enable_query_log +-- enable_result_log + +insert into t2 select id from t1; + +create table t3 (kill_id int); +insert into t3 values(connection_id()); + +-- disable_result_log +send select id from t1 where id in (select distinct id from t2); +-- enable_result_log + +connect (conn2, localhost, root,,); +connection conn2; +select ((@id := kill_id) - kill_id) from t3; +-- sleep 1 +kill @id; + +connection conn1; +-- error 1053 +reap; + +disconnect conn1; +disconnect conn2; +connection default; + +drop table t1, t2, t3; + # End of 4.1 tests diff --git a/sql/sql_class.cc b/sql/sql_class.cc index 947da6b10d6..cdce9b6c7bc 100644 --- a/sql/sql_class.cc +++ b/sql/sql_class.cc @@ -1681,7 +1681,10 @@ bool select_dumpvar::send_eof() void TMP_TABLE_PARAM::init() { + DBUG_ENTER("TMP_TABLE_PARAM::init"); + DBUG_PRINT("enter", ("this: 0x%lx", (ulong)this)); field_count= sum_func_count= func_count= hidden_field_count= 0; group_parts= group_length= group_null_parts= 0; quick_group= 1; + DBUG_VOID_RETURN; } diff --git a/sql/sql_select.cc b/sql/sql_select.cc index 5ef3f4d9fda..aca2c72f1ea 100644 --- a/sql/sql_select.cc +++ b/sql/sql_select.cc @@ -4107,6 +4107,20 @@ JOIN::join_free(bool full) problems in free_elements() as some of the elements are then deleted. */ tmp_table_param.copy_funcs.empty(); + /* + If we have tmp_join and 'this' JOIN is not tmp_join and + tmp_table_param.copy_field's of them are equal then we have to remove + pointer to tmp_table_param.copy_field from tmp_join, because it qill + be removed in tmp_table_param.cleanup(). + */ + if (tmp_join && + tmp_join != this && + tmp_join->tmp_table_param.copy_field == + tmp_table_param.copy_field) + { + tmp_join->tmp_table_param.copy_field= + tmp_join->tmp_table_param.save_copy_field= 0; + } tmp_table_param.cleanup(); } DBUG_VOID_RETURN; diff --git a/sql/sql_select.h b/sql/sql_select.h index 636ee967645..94cc8839466 100644 --- a/sql/sql_select.h +++ b/sql/sql_select.h @@ -227,7 +227,14 @@ class JOIN :public Sql_alloc { init(thd_arg, fields_arg, select_options_arg, result_arg); } - + + JOIN(JOIN &join) + :fields_list(join.fields_list) + { + init(join.thd, join.fields_list, join.select_options, + join.result); + } + void init(THD *thd_arg, List<Item> &fields_arg, ulong select_options_arg, select_result *result_arg) { @@ -272,7 +279,7 @@ class JOIN :public Sql_alloc fields_list= fields_arg; bzero((char*) &keyuse,sizeof(keyuse)); - tmp_table_param.copy_field=0; + tmp_table_param.init(); tmp_table_param.end_write_records= HA_POS_ERROR; rollup.state= ROLLUP::STATE_NONE; } |