diff options
author | unknown <bar@mysql.com> | 2005-11-21 17:26:31 +0400 |
---|---|---|
committer | unknown <bar@mysql.com> | 2005-11-21 17:26:31 +0400 |
commit | 72d19611d198164e1fcd2e16b270a11824d860bf (patch) | |
tree | 05c91bc3d02c0f22aab0913b8e7228667bb5ff38 /sql/item_strfunc.h | |
parent | 83bbd30c480d97f57203b999cff4517f5e04bf13 (diff) | |
download | mariadb-git-72d19611d198164e1fcd2e16b270a11824d860bf.tar.gz |
Bug#10446 Illegal mix of collations:
item_strfunc.h, item_strfunc.cc, item.cc:
Try to convert a const item into destination
character set. If conversion happens without
data loss, then cache the converted value
and return it during val_str().
Otherwise, if conversion loses data, return
Illeral mix of collations error, as it happened
previously.
ctype_recoding.result, ctype_recoding.test:
Fixing tests accordingly.
sql/item.cc:
Bug#10446 Illegal mix of collations
Try to convert a const item into destination
character set. If conversion happens without
data loss, then cache the converted value
and return it during val_str().
Otherwise, if conversion loses data, return
Illeral mix of collations error, as it happened
previously.
sql/item_strfunc.cc:
Return cached value when it's possible.
mysql-test/t/ctype_recoding.test:
Fixing tests accordingly.
mysql-test/r/ctype_recoding.result:
Fixing tests accordingly.
Diffstat (limited to 'sql/item_strfunc.h')
-rw-r--r-- | sql/item_strfunc.h | 34 |
1 files changed, 32 insertions, 2 deletions
diff --git a/sql/item_strfunc.h b/sql/item_strfunc.h index 87aee9ac25c..c4505fce248 100644 --- a/sql/item_strfunc.h +++ b/sql/item_strfunc.h @@ -614,10 +614,40 @@ public: class Item_func_conv_charset :public Item_str_func { + bool use_cached_value; public: + bool safe; CHARSET_INFO *conv_charset; // keep it public - Item_func_conv_charset(Item *a, CHARSET_INFO *cs) :Item_str_func(a) - { conv_charset=cs; } + Item_func_conv_charset(Item *a, CHARSET_INFO *cs) :Item_str_func(a) + { conv_charset= cs; use_cached_value= 0; safe= 0; } + Item_func_conv_charset(Item *a, CHARSET_INFO *cs, bool cache_if_const) + :Item_str_func(a) + { + DBUG_ASSERT(args[0]->fixed); + conv_charset= cs; + if (cache_if_const && args[0]->const_item()) + { + uint errors= 0; + String tmp, *str= args[0]->val_str(&tmp); + if (!str || str_value.copy(str->ptr(), str->length(), + str->charset(), conv_charset, &errors)) + null_value= 1; + use_cached_value= 1; + safe= (errors == 0); + } + else + { + use_cached_value= 0; + /* + Conversion from and to "binary" is safe. + Conversion to Unicode is safe. + Other kind of conversions are potentially lossy. + */ + safe= (args[0]->collation.collation == &my_charset_bin || + cs == &my_charset_bin || + (cs->state & MY_CS_UNICODE)); + } + } String *val_str(String *); void fix_length_and_dec(); const char *func_name() const { return "convert"; } |