diff options
author | Alexander Barkov <bar@mariadb.org> | 2018-01-30 11:07:35 +0400 |
---|---|---|
committer | Alexander Barkov <bar@mariadb.org> | 2018-01-30 11:07:35 +0400 |
commit | dae4fb0acb373e653f826f0ec7bdaf2485ef0b93 (patch) | |
tree | ea66ce3c195373f913f45d76286f1c5e4123cfdb | |
parent | b76881a23cff7aeef1126560410613d9d7bbbb7d (diff) | |
download | mariadb-git-dae4fb0acb373e653f826f0ec7bdaf2485ef0b93.tar.gz |
MDEV-15118 ExtractValue(xml,something_complex) does not work
Item_xml_str_func::fix_fields() used a local "String tmp" as a buffer
for args[1]->val_str(). "tmp" was freed at the end of fix_fields(),
while Items created during my_xpath_parse() still pointed to its fragments.
Adding a new member Item_xml_str_func::m_xpath_query and store the result
of args[1]->val_str() into it.
-rw-r--r-- | mysql-test/r/xml.result | 12 | ||||
-rw-r--r-- | mysql-test/t/xml.test | 9 | ||||
-rw-r--r-- | sql/item_xmlfunc.cc | 10 | ||||
-rw-r--r-- | sql/item_xmlfunc.h | 1 |
4 files changed, 30 insertions, 2 deletions
diff --git a/mysql-test/r/xml.result b/mysql-test/r/xml.result index 24b95f0e204..b12243bdfb9 100644 --- a/mysql-test/r/xml.result +++ b/mysql-test/r/xml.result @@ -1268,5 +1268,17 @@ c1 c2 2 b2 DROP TABLE t1; # +# MDEV-15118 ExtractValue(xml,something_complex) does not work +# +CREATE TABLE t1 (a TEXT); +INSERT INTO t1 VALUES (CONCAT('<a>aaa</a>')); +SELECT ExtractValue(a, '/a') AS a FROM t1; +a +aaa +SELECT ExtractValue(a, FROM_BASE64(TO_BASE64('/a'))) AS a FROM t1; +a +aaa +DROP TABLE t1; +# # End of 10.0 tests # diff --git a/mysql-test/t/xml.test b/mysql-test/t/xml.test index 371fcb72b0d..e9e7864c418 100644 --- a/mysql-test/t/xml.test +++ b/mysql-test/t/xml.test @@ -748,6 +748,15 @@ SELECT *,IF(@i:=c1,ExtractValue('<a><b>b1</b><b>b2</b></a>','//b[$@i]'),0) AS xp SELECT * FROM t1 WHERE c2=IF(@i:=c1,ExtractValue('<a><b>b1</b><b>b2</b></a>','//b[$@i]'),0); DROP TABLE t1; +--echo # +--echo # MDEV-15118 ExtractValue(xml,something_complex) does not work +--echo # + +CREATE TABLE t1 (a TEXT); +INSERT INTO t1 VALUES (CONCAT('<a>aaa</a>')); +SELECT ExtractValue(a, '/a') AS a FROM t1; +SELECT ExtractValue(a, FROM_BASE64(TO_BASE64('/a'))) AS a FROM t1; +DROP TABLE t1; --echo # --echo # End of 10.0 tests diff --git a/sql/item_xmlfunc.cc b/sql/item_xmlfunc.cc index c7fd923b0ae..c12f5fd3e87 100644 --- a/sql/item_xmlfunc.cc +++ b/sql/item_xmlfunc.cc @@ -2634,7 +2634,7 @@ void Item_xml_str_func::fix_length_and_dec() bool Item_xml_str_func::fix_fields(THD *thd, Item **ref) { - String *xp, tmp; + String *xp; MY_XPATH xpath; int rc; @@ -2662,7 +2662,13 @@ bool Item_xml_str_func::fix_fields(THD *thd, Item **ref) return true; } - if (!(xp= args[1]->val_str(&tmp))) + /* + Get the XPath query text from args[1] and cache it in m_xpath_query. + Its fragments will be referenced by items created during my_xpath_parse(), + e.g. by Item_nodeset_func_axisbyname::node_name. + */ + if (!(xp= args[1]->val_str(&m_xpath_query)) || + (xp != &m_xpath_query && m_xpath_query.copy(*xp))) return false; // Will return NULL my_xpath_init(&xpath); xpath.cs= collation.collation; diff --git a/sql/item_xmlfunc.h b/sql/item_xmlfunc.h index 637f505e12e..e0356d367bd 100644 --- a/sql/item_xmlfunc.h +++ b/sql/item_xmlfunc.h @@ -67,6 +67,7 @@ protected: return parse(res, cache); } }; + String m_xpath_query; // XPath query text Item *nodeset_func; XML xml; bool get_xml(XML *xml, bool cache= false) |