From: Tor Didriksen Date: February 22 2012 9:26am Subject: bzr push into mysql-trunk branch (tor.didriksen:3940 to 3941) Bug#13724099 List-Archive: http://lists.mysql.com/commits/143024 X-Bug: 13724099 Message-Id: <201202220926.q1M9QmJU006988@acsmt358.oracle.com> MIME-Version: 1.0 Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit 3941 Tor Didriksen 2012-02-22 Bug#13724099 1032 BYTE MEMORY LEAK NEW_CACHED_ITEM IN SUBQUERY WITH GROUPING OF OUTER COLUMN JOIN::cleanup didn't run delete_elements on the group_fileds list. @ sql/sql_list.h Add bool base_ilist::operator==(const base_list &rhs) const Cleanup code which was commented out. @ sql/sql_select.cc tmp_join->group_fields was emptied without running delete_elements(). Rewrote the logic for avoiding double-delete on the list. modified: mysql-test/r/func_group.result mysql-test/t/func_group.test sql/sql_list.h sql/sql_select.cc 3940 Tor Didriksen 2012-02-22 Bug#12677197 MAKE_SET() AND MY_EMPTY_STRING BUGS CAUSE CRASHING The patch for: Bug#11765225 58165: "MY_EMPTY_STRING" GETS MODIFIED AND CAUSES LOAD DATA TO FAIL AND OTHER CR removed most uses of my_empty_string. This patch removes it as a global variable, and makes it (and a few others) const, so that it cannot be modified. @ client/sql_string.cc Make String::numchars() a const member function. @ client/sql_string.h Make String::numchars() a const member function. @ mysql-test/r/func_set.result New tests. @ mysql-test/t/func_set.test New tests. @ sql/item_strfunc.cc Don't use my_empty_string, use make_empty_result() instead. @ sql/item_strfunc.h Remove the global my_empty_string. @ sql/log_event.cc Do not modify a string which might be constant. @ sql/sql_class.cc Constify a few static, default values. @ sql/sql_class.h Several of the string pointers in sql_exchange may point to const strings, so declare them 'const String *' rather than 'String *'. @ sql/sql_load.cc Constify a few string pointers/references. @ sql/sql_string.cc Make String::numchars() a const member function. @ sql/sql_string.h Make String::numchars() a const member function. modified: client/sql_string.cc client/sql_string.h mysql-test/r/func_set.result mysql-test/t/func_set.test sql/item_strfunc.cc sql/item_strfunc.h sql/log_event.cc sql/sql_class.cc sql/sql_class.h sql/sql_load.cc sql/sql_string.cc sql/sql_string.h === modified file 'mysql-test/r/func_group.result' --- a/mysql-test/r/func_group.result 2011-12-22 13:36:08 +0000 +++ b/mysql-test/r/func_group.result 2012-02-22 09:26:19 +0000 @@ -1813,3 +1813,19 @@ SELECT MAX(a) FROM t1 WHERE a NOT BETWEE MAX(a) 10 DROP TABLE t1; +# +# Bug#13724099 1032 BYTE MEMORY LEAK NEW_CACHED_ITEM IN +# SUBQUERY WITH GROUPING OF OUTER COLUMN +# +CREATE TABLE t1 ( +a BLOB, +b INT) +engine=innodb; +INSERT INTO t1 VALUES ('a', 0); +SELECT 0 FROM t1 +WHERE 0 = (SELECT group_concat(b) +FROM t1 t GROUP BY t1.a) +; +0 +0 +DROP TABLE t1; === modified file 'mysql-test/t/func_group.test' --- a/mysql-test/t/func_group.test 2011-12-22 13:36:08 +0000 +++ b/mysql-test/t/func_group.test 2012-02-22 09:26:19 +0000 @@ -1193,3 +1193,21 @@ INSERT INTO t1 VALUES (1),(2),(3),(4),(5 SELECT MAX(a) FROM t1 WHERE a NOT BETWEEN 3 AND 9; DROP TABLE t1; + +--echo # +--echo # Bug#13724099 1032 BYTE MEMORY LEAK NEW_CACHED_ITEM IN +--echo # SUBQUERY WITH GROUPING OF OUTER COLUMN +--echo # + +CREATE TABLE t1 ( + a BLOB, + b INT) +engine=innodb; + +INSERT INTO t1 VALUES ('a', 0); + +SELECT 0 FROM t1 +WHERE 0 = (SELECT group_concat(b) + FROM t1 t GROUP BY t1.a) +; +DROP TABLE t1; === modified file 'sql/sql_list.h' --- a/sql/sql_list.h 2012-02-15 13:57:17 +0000 +++ b/sql/sql_list.h 2012-02-22 09:26:19 +0000 @@ -185,6 +185,14 @@ protected: public: uint elements; + bool operator==(const base_list &rhs) const + { + return + elements == rhs.elements && + first == rhs.first && + last == rhs.last; + } + inline void empty() { elements=0; first= &end_of_list; last=&first;} inline base_list() { empty(); } /** @@ -521,17 +529,8 @@ public: } empty(); } - /** - @brief - Sort the list according to provided comparison function - @param cmp node comparison function - @param arg additional info to be passed to comparison function - * / - inline void sort(Node_cmp_func cmp, void *arg) - { - base_list::sort(cmp, arg); - }*/ + using base_list::sort; }; === modified file 'sql/sql_select.cc' --- a/sql/sql_select.cc 2012-02-21 10:31:44 +0000 +++ b/sql/sql_select.cc 2012-02-22 09:26:19 +0000 @@ -700,6 +700,8 @@ static int clear_sj_tmp_tables(JOIN *joi */ void JOIN::restore_tmp() { + DBUG_PRINT("info", ("restore_tmp this %p tmp_join %p", this, tmp_join)); + DBUG_ASSERT(tmp_join != this); memcpy(tmp_join, this, (size_t) sizeof(JOIN)); } @@ -3151,13 +3153,18 @@ void JOIN::cleanup(bool full) { if (tmp_join) tmp_table_param.copy_field= 0; - group_fields.delete_elements(); + /* - Ensure that the above delete_elements() would not be called + Ensure that the following delete_elements() would not be called twice for the same list. */ - if (tmp_join && tmp_join != this) - tmp_join->group_fields= group_fields; + if (tmp_join && tmp_join != this && + tmp_join->group_fields == this->group_fields) + tmp_join->group_fields.empty(); + + // Run Cached_item DTORs! + group_fields.delete_elements(); + /* We can't call delete_elements() on copy_funcs as this will cause problems in free_elements() as some of the elements are then deleted. No bundle (reason: useless for push emails).