diff options
author | Gleb Shchepa <gshchepa@mysql.com> | 2010-01-13 08:16:36 +0400 |
---|---|---|
committer | Gleb Shchepa <gshchepa@mysql.com> | 2010-01-13 08:16:36 +0400 |
commit | 71fd38e488d1d10210c9c5370f56d682d9884814 (patch) | |
tree | 58a509d3bb942aa20b969bd71f60c829dfbba7f3 | |
parent | 3c9322e73f5b994b7ec13ed73e99ce4bc94694b8 (diff) | |
download | mariadb-git-71fd38e488d1d10210c9c5370f56d682d9884814.tar.gz |
Bug #50096: CONCAT_WS inside procedure returning wrong data
Selecting of the CONCAT_WS(...<PS parameter>...) result into
a user variable may return wrong data.
Item_func_concat_ws::val_str contains a number of memory
allocation-saving optimization tricks. After the fix
for bug 46815 the control flow has been changed to a
branch that is commented as "This is quite uncommon!":
one of places where we are trying to concatenate
strings inplace. However, that "uncommon" place
didn't care about PS parameters, that have another
trick in Item_sp_variable::val_str(): they use the
intermediate Item_sp_variable::str_value field,
where they may store a reference to an external
argument's buffer.
The Item_func_concat_ws::val_str function has been
modified to take into account val_str functions
(such as Item_sp_variable::val_str) that return a
pointer to an internal Item member variable that
may reference to a buffer provided.
mysql-test/r/func_concat.result:
Added test case for bug #50096.
mysql-test/t/func_concat.test:
Added test case for bug #50096.
sql/item_strfunc.cc:
Bug #50096: CONCAT_WS inside procedure returning wrong data
The Item_func_concat_ws::val_str function has been
modified to take into account val_str functions
(such as Item_sp_variable::val_str) that return a
pointer to an internal Item member variable that
may reference to a buffer provided.
-rw-r--r-- | mysql-test/r/func_concat.result | 11 | ||||
-rw-r--r-- | mysql-test/t/func_concat.test | 13 | ||||
-rw-r--r-- | sql/item_strfunc.cc | 4 |
3 files changed, 26 insertions, 2 deletions
diff --git a/mysql-test/r/func_concat.result b/mysql-test/r/func_concat.result index 75b4888fbb2..c4c2b46c6c2 100644 --- a/mysql-test/r/func_concat.result +++ b/mysql-test/r/func_concat.result @@ -1,4 +1,5 @@ DROP TABLE IF EXISTS t1; +DROP PROCEDURE IF EXISTS p1; CREATE TABLE t1 ( number INT NOT NULL, alpha CHAR(6) NOT NULL ); INSERT INTO t1 VALUES (1413006,'idlfmv'), (1413065,'smpsfz'),(1413127,'sljrhx'),(1413304,'qerfnd'); @@ -119,4 +120,14 @@ id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t2 index NULL PRIMARY 102 NULL 3 Using index 1 SIMPLE t1 eq_ref PRIMARY,a PRIMARY 318 func,const,const 1 DROP TABLE t1, t2; +# +# Bug #50096: CONCAT_WS inside procedure returning wrong data +# +CREATE PROCEDURE p1(a varchar(255), b int, c int) +SET @query = CONCAT_WS(",", a, b, c); +CALL p1("abcde", "0", "1234"); +SELECT @query; +@query +abcde,0,1234 +DROP PROCEDURE p1; # End of 5.1 tests diff --git a/mysql-test/t/func_concat.test b/mysql-test/t/func_concat.test index 1c7e5823fb2..e24b4354b61 100644 --- a/mysql-test/t/func_concat.test +++ b/mysql-test/t/func_concat.test @@ -4,6 +4,7 @@ --disable_warnings DROP TABLE IF EXISTS t1; +DROP PROCEDURE IF EXISTS p1; --enable_warnings CREATE TABLE t1 ( number INT NOT NULL, alpha CHAR(6) NOT NULL ); @@ -111,4 +112,16 @@ EXPLAIN SELECT CONCAT('gui_', t2.a), t1.d FROM t2 DROP TABLE t1, t2; +--echo # +--echo # Bug #50096: CONCAT_WS inside procedure returning wrong data +--echo # + +CREATE PROCEDURE p1(a varchar(255), b int, c int) + SET @query = CONCAT_WS(",", a, b, c); + +CALL p1("abcde", "0", "1234"); +SELECT @query; + +DROP PROCEDURE p1; + --echo # End of 5.1 tests diff --git a/sql/item_strfunc.cc b/sql/item_strfunc.cc index b6d3f45f4c2..ecd839d8378 100644 --- a/sql/item_strfunc.cc +++ b/sql/item_strfunc.cc @@ -677,8 +677,8 @@ String *Item_func_concat_ws::val_str(String *str) res->length() + sep_str->length() + res2->length()) { /* We have room in str; We can't get any errors here */ - if (str == res2) - { // This is quote uncommon! + if (str->ptr() == res2->ptr()) + { // This is quite uncommon! str->replace(0,0,*sep_str); str->replace(0,0,*res); } |