From 850d3bafcae1aeeb4470886408e19c084d9d183e Mon Sep 17 00:00:00 2001 From: halfspawn Date: Wed, 3 May 2017 17:39:45 +0200 Subject: [PATCH] MDEV-12658 Make the third parameter to LPAD and RPAD optional --- mysql-test/r/func_str.result | 184 +++++++++++++++++++++++++++++++++++ mysql-test/t/func_str.test | 53 +++++++++- sql/item_create.cc | 68 +++++++++++-- sql/item_strfunc.cc | 53 +++++++--- sql/item_strfunc.h | 6 ++ 5 files changed, 344 insertions(+), 20 deletions(-) diff --git a/mysql-test/r/func_str.result b/mysql-test/r/func_str.result index 8a1302c9b5cda..9d3e5587426ca 100644 --- a/mysql-test/r/func_str.result +++ b/mysql-test/r/func_str.result @@ -297,6 +297,9 @@ STRINGpadpadpadpadpa select lpad('STRING', 20, CONCAT('p','a','d') ); lpad('STRING', 20, CONCAT('p','a','d') ) padpadpadpadpaSTRING +select rpad('abcd',7),lpad('abcd',7); +rpad('abcd',7) lpad('abcd',7) +abcd abcd select LEAST(NULL,'HARRY','HARRIOT',NULL,'HAROLD'),GREATEST(NULL,'HARRY','HARRIOT',NULL,'HAROLD'); LEAST(NULL,'HARRY','HARRIOT',NULL,'HAROLD') GREATEST(NULL,'HARRY','HARRIOT',NULL,'HAROLD') NULL NULL @@ -637,9 +640,15 @@ latin2_general_ci 4 select collation(lpad(_latin2'a',4,_latin2'b')), coercibility(lpad(_latin2'a',4,_latin2'b')); collation(lpad(_latin2'a',4,_latin2'b')) coercibility(lpad(_latin2'a',4,_latin2'b')) latin2_general_ci 4 +select collation(lpad(_latin2'a',4)), coercibility(lpad(_latin2'a',4)); +collation(lpad(_latin2'a',4)) coercibility(lpad(_latin2'a',4)) +latin2_general_ci 4 select collation(rpad(_latin2'a',4,_latin2'b')), coercibility(rpad(_latin2'a',4,_latin2'b')); collation(rpad(_latin2'a',4,_latin2'b')) coercibility(rpad(_latin2'a',4,_latin2'b')) latin2_general_ci 4 +select collation(rpad(_latin2'a',4)), coercibility(rpad(_latin2'a',4)); +collation(rpad(_latin2'a',4)) coercibility(rpad(_latin2'a',4)) +latin2_general_ci 4 select collation(concat_ws(_latin2'a',_latin2'b')), coercibility(concat_ws(_latin2'a',_latin2'b')); collation(concat_ws(_latin2'a',_latin2'b')) coercibility(concat_ws(_latin2'a',_latin2'b')) latin2_general_ci 4 @@ -707,6 +716,8 @@ substring(_latin2'a',1,1), concat(_latin2'a',_latin2'b'), lpad(_latin2'a',4,_latin2'b'), rpad(_latin2'a',4,_latin2'b'), +lpad(_latin2'a',4), +rpad(_latin2'a',4), concat_ws(_latin2'a',_latin2'b'), make_set(255,_latin2'a',_latin2'b',_latin2'c'), export_set(255,_latin2'y',_latin2'n',_latin2' '), @@ -742,6 +753,8 @@ t1 CREATE TABLE `t1` ( `concat(_latin2'a',_latin2'b')` varchar(2) CHARACTER SET latin2 DEFAULT NULL, `lpad(_latin2'a',4,_latin2'b')` varchar(4) CHARACTER SET latin2 DEFAULT NULL, `rpad(_latin2'a',4,_latin2'b')` varchar(4) CHARACTER SET latin2 DEFAULT NULL, + `lpad(_latin2'a',4)` varchar(4) CHARACTER SET latin2 DEFAULT NULL, + `rpad(_latin2'a',4)` varchar(4) CHARACTER SET latin2 DEFAULT NULL, `concat_ws(_latin2'a',_latin2'b')` varchar(1) CHARACTER SET latin2 DEFAULT NULL, `make_set(255,_latin2'a',_latin2'b',_latin2'c')` varchar(5) CHARACTER SET latin2 DEFAULT NULL, `export_set(255,_latin2'y',_latin2'n',_latin2' ')` varchar(127) CHARACTER SET latin2 DEFAULT NULL, @@ -869,6 +882,16 @@ id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE NULL NULL NULL NULL NULL NULL NULL NULL No tables used Warnings: Note 1003 select lpad('a',4,'1') AS `lpad('a',4,'1')` +explain extended select rpad('a',4); +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE NULL NULL NULL NULL NULL NULL NULL NULL No tables used +Warnings: +Note 1003 select rpad('a',4) AS `rpad('a',4)` +explain extended select lpad('a',4); +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE NULL NULL NULL NULL NULL NULL NULL NULL No tables used +Warnings: +Note 1003 select lpad('a',4) AS `lpad('a',4)` explain extended select concat_ws(',','',NULL,'a'); id select_type table type possible_keys key key_len ref rows filtered Extra 1 SIMPLE NULL NULL NULL NULL NULL NULL NULL NULL No tables used @@ -2213,6 +2236,76 @@ Warnings: Warning 1916 Got overflow when converting '18446744073709551617' to INT. Value truncated Warning 1916 Got overflow when converting '18446744073709551617' to INT. Value truncated Warning 1301 Result of rpad() was larger than max_allowed_packet (1048576) - truncated +select rpad('hello', -1); +rpad('hello', -1) +NULL +select rpad('hello', -4294967295); +rpad('hello', -4294967295) +NULL +select rpad('hello', 4294967295); +rpad('hello', 4294967295) +NULL +Warnings: +Warning 1301 Result of rpad() was larger than max_allowed_packet (1048576) - truncated +select rpad('hello', -4294967296); +rpad('hello', -4294967296) +NULL +select rpad('hello', 4294967296); +rpad('hello', 4294967296) +NULL +Warnings: +Warning 1301 Result of rpad() was larger than max_allowed_packet (1048576) - truncated +select rpad('hello', -4294967297); +rpad('hello', -4294967297) +NULL +select rpad('hello', 4294967297); +rpad('hello', 4294967297) +NULL +Warnings: +Warning 1301 Result of rpad() was larger than max_allowed_packet (1048576) - truncated +select rpad('hello', -18446744073709551615); +rpad('hello', -18446744073709551615) +NULL +Warnings: +Warning 1916 Got overflow when converting '-18446744073709551615' to INT. Value truncated +Warning 1916 Got overflow when converting '-18446744073709551615' to INT. Value truncated +select rpad('hello', 18446744073709551615); +rpad('hello', 18446744073709551615) +NULL +Warnings: +Warning 1301 Result of rpad() was larger than max_allowed_packet (1048576) - truncated +select rpad('hello', -18446744073709551616); +rpad('hello', -18446744073709551616) +NULL +Warnings: +Warning 1916 Got overflow when converting '-18446744073709551616' to INT. Value truncated +Warning 1916 Got overflow when converting '-18446744073709551616' to INT. Value truncated +select rpad('hello', 18446744073709551616); +rpad('hello', 18446744073709551616) +NULL +Warnings: +Warning 1916 Got overflow when converting '18446744073709551616' to INT. Value truncated +Warning 1916 Got overflow when converting '18446744073709551616' to INT. Value truncated +Warning 1301 Result of rpad() was larger than max_allowed_packet (1048576) - truncated +select rpad('hello', -18446744073709551617); +rpad('hello', -18446744073709551617) +NULL +Warnings: +Warning 1916 Got overflow when converting '-18446744073709551617' to INT. Value truncated +Warning 1916 Got overflow when converting '-18446744073709551617' to INT. Value truncated +select rpad('hello', 18446744073709551617); +rpad('hello', 18446744073709551617) +NULL +Warnings: +Warning 1916 Got overflow when converting '18446744073709551617' to INT. Value truncated +Warning 1916 Got overflow when converting '18446744073709551617' to INT. Value truncated +Warning 1301 Result of rpad() was larger than max_allowed_packet (1048576) - truncated +select rpad('hello', 0, 'x'); +rpad('hello', 0, 'x') + +select rpad('hello', 0); +rpad('hello', 0) + select lpad('hello', -1, '1'); lpad('hello', -1, '1') NULL @@ -2277,6 +2370,85 @@ Warnings: Warning 1916 Got overflow when converting '18446744073709551617' to INT. Value truncated Warning 1916 Got overflow when converting '18446744073709551617' to INT. Value truncated Warning 1301 Result of lpad() was larger than max_allowed_packet (1048576) - truncated +select lpad('hello', -1); +lpad('hello', -1) +NULL +select lpad('hello', -4294967295); +lpad('hello', -4294967295) +NULL +select lpad('hello', 4294967295); +lpad('hello', 4294967295) +NULL +Warnings: +Warning 1301 Result of lpad() was larger than max_allowed_packet (1048576) - truncated +select lpad('hello', -4294967296); +lpad('hello', -4294967296) +NULL +select lpad('hello', 4294967296); +lpad('hello', 4294967296) +NULL +Warnings: +Warning 1301 Result of lpad() was larger than max_allowed_packet (1048576) - truncated +select lpad('hello', -4294967297); +lpad('hello', -4294967297) +NULL +select lpad('hello', 4294967297); +lpad('hello', 4294967297) +NULL +Warnings: +Warning 1301 Result of lpad() was larger than max_allowed_packet (1048576) - truncated +select lpad('hello', -18446744073709551615); +lpad('hello', -18446744073709551615) +NULL +Warnings: +Warning 1916 Got overflow when converting '-18446744073709551615' to INT. Value truncated +Warning 1916 Got overflow when converting '-18446744073709551615' to INT. Value truncated +select lpad('hello', 18446744073709551615); +lpad('hello', 18446744073709551615) +NULL +Warnings: +Warning 1301 Result of lpad() was larger than max_allowed_packet (1048576) - truncated +select lpad('hello', -18446744073709551616); +lpad('hello', -18446744073709551616) +NULL +Warnings: +Warning 1916 Got overflow when converting '-18446744073709551616' to INT. Value truncated +Warning 1916 Got overflow when converting '-18446744073709551616' to INT. Value truncated +select lpad('hello', 18446744073709551616); +lpad('hello', 18446744073709551616) +NULL +Warnings: +Warning 1916 Got overflow when converting '18446744073709551616' to INT. Value truncated +Warning 1916 Got overflow when converting '18446744073709551616' to INT. Value truncated +Warning 1301 Result of lpad() was larger than max_allowed_packet (1048576) - truncated +select lpad('hello', -18446744073709551617); +lpad('hello', -18446744073709551617) +NULL +Warnings: +Warning 1916 Got overflow when converting '-18446744073709551617' to INT. Value truncated +Warning 1916 Got overflow when converting '-18446744073709551617' to INT. Value truncated +select lpad('hello', 18446744073709551617); +lpad('hello', 18446744073709551617) +NULL +Warnings: +Warning 1916 Got overflow when converting '18446744073709551617' to INT. Value truncated +Warning 1916 Got overflow when converting '18446744073709551617' to INT. Value truncated +Warning 1301 Result of lpad() was larger than max_allowed_packet (1048576) - truncated +select lpad('hello', 0, 'x'); +lpad('hello', 0, 'x') + +select lpad('hello', 0); +lpad('hello', 0) + +Check parameters count rpad / lpad +select rpad('x'); +ERROR 42000: Incorrect parameter count in the call to native function 'rpad' +select rpad('x',2,'.','z'); +ERROR 42000: Incorrect parameter count in the call to native function 'rpad' +select lpad('x'); +ERROR 42000: Incorrect parameter count in the call to native function 'lpad' +select lpad('x',2,'.','z'); +ERROR 42000: Incorrect parameter count in the call to native function 'lpad' SET @orig_sql_mode = @@SQL_MODE; SET SQL_MODE=traditional; SELECT CHAR(0xff,0x8f USING utf8); @@ -2302,6 +2474,12 @@ abcxx select lpad('abc', cast(5 as unsigned integer), 'x'); lpad('abc', cast(5 as unsigned integer), 'x') xxabc +select rpad('abc', cast(5 as unsigned integer)); +rpad('abc', cast(5 as unsigned integer)) +abc +select lpad('abc', cast(5 as unsigned integer)); +lpad('abc', cast(5 as unsigned integer)) + abc create table t1(f1 longtext); insert into t1 values ("123"),("456"); select substring(f1,1,1) from t1 group by 1; @@ -2663,6 +2841,12 @@ NULL SELECT LPAD('hi', DAY(FROM_UNIXTIME(-1)),'?'); LPAD('hi', DAY(FROM_UNIXTIME(-1)),'?') NULL +SELECT RPAD('hi', DAY(FROM_UNIXTIME(-1))); +RPAD('hi', DAY(FROM_UNIXTIME(-1))) +NULL +SELECT LPAD('hi', DAY(FROM_UNIXTIME(-1))); +LPAD('hi', DAY(FROM_UNIXTIME(-1))) +NULL create table t1 (i int); insert into t1 values (null),(8); select group_concat( i ), make_set( i, 'a', 'b' ) field from t1 group by field; diff --git a/mysql-test/t/func_str.test b/mysql-test/t/func_str.test index b3f6b4faf499f..bb3251b3e31da 100644 --- a/mysql-test/t/func_str.test +++ b/mysql-test/t/func_str.test @@ -119,6 +119,7 @@ select rpad('abcd',7,'ab'),lpad('abcd',7,'ab'); select rpad('abcd',1,'ab'),lpad('abcd',1,'ab'); select rpad('STRING', 20, CONCAT('p','a','d') ); select lpad('STRING', 20, CONCAT('p','a','d') ); +select rpad('abcd',7),lpad('abcd',7); select LEAST(NULL,'HARRY','HARRIOT',NULL,'HAROLD'),GREATEST(NULL,'HARRY','HARRIOT',NULL,'HAROLD'); select least(1,2,3) | greatest(16,32,8), least(5,4)*1,greatest(-1.0,1.0)*1,least(3,2,1)*1.0,greatest(1,1.1,1.0),least("10",9),greatest("A","B","0"); @@ -373,7 +374,9 @@ select collation(right(_latin2'a',1)), coercibility(right(_latin2'a',1)); select collation(substring(_latin2'a',1,1)), coercibility(substring(_latin2'a',1,1)); select collation(concat(_latin2'a',_latin2'b')), coercibility(concat(_latin2'a',_latin2'b')); select collation(lpad(_latin2'a',4,_latin2'b')), coercibility(lpad(_latin2'a',4,_latin2'b')); +select collation(lpad(_latin2'a',4)), coercibility(lpad(_latin2'a',4)); select collation(rpad(_latin2'a',4,_latin2'b')), coercibility(rpad(_latin2'a',4,_latin2'b')); +select collation(rpad(_latin2'a',4)), coercibility(rpad(_latin2'a',4)); select collation(concat_ws(_latin2'a',_latin2'b')), coercibility(concat_ws(_latin2'a',_latin2'b')); select collation(make_set(255,_latin2'a',_latin2'b',_latin2'c')), coercibility(make_set(255,_latin2'a',_latin2'b',_latin2'c')); select collation(export_set(255,_latin2'y',_latin2'n',_latin2' ')), coercibility(export_set(255,_latin2'y',_latin2'n',_latin2' ')); @@ -408,6 +411,8 @@ select concat(_latin2'a',_latin2'b'), lpad(_latin2'a',4,_latin2'b'), rpad(_latin2'a',4,_latin2'b'), + lpad(_latin2'a',4), + rpad(_latin2'a',4), concat_ws(_latin2'a',_latin2'b'), make_set(255,_latin2'a',_latin2'b',_latin2'c'), export_set(255,_latin2'y',_latin2'n',_latin2' '), @@ -485,6 +490,8 @@ explain extended select concat('*',space(5),'*'); explain extended select reverse('abc'); explain extended select rpad('a',4,'1'); explain extended select lpad('a',4,'1'); +explain extended select rpad('a',4); +explain extended select lpad('a',4); explain extended select concat_ws(',','',NULL,'a'); explain extended select make_set(255,_latin2'a', _latin2'b', _latin2'c'); explain extended select elt(2,1); @@ -1105,6 +1112,21 @@ select rpad('hello', -18446744073709551616, '1'); select rpad('hello', 18446744073709551616, '1'); select rpad('hello', -18446744073709551617, '1'); select rpad('hello', 18446744073709551617, '1'); +select rpad('hello', -1); +select rpad('hello', -4294967295); +select rpad('hello', 4294967295); +select rpad('hello', -4294967296); +select rpad('hello', 4294967296); +select rpad('hello', -4294967297); +select rpad('hello', 4294967297); +select rpad('hello', -18446744073709551615); +select rpad('hello', 18446744073709551615); +select rpad('hello', -18446744073709551616); +select rpad('hello', 18446744073709551616); +select rpad('hello', -18446744073709551617); +select rpad('hello', 18446744073709551617); +select rpad('hello', 0, 'x'); +select rpad('hello', 0); select lpad('hello', -1, '1'); select lpad('hello', -4294967295, '1'); @@ -1119,7 +1141,32 @@ select lpad('hello', -18446744073709551616, '1'); select lpad('hello', 18446744073709551616, '1'); select lpad('hello', -18446744073709551617, '1'); select lpad('hello', 18446744073709551617, '1'); - +select lpad('hello', -1); +select lpad('hello', -4294967295); +select lpad('hello', 4294967295); +select lpad('hello', -4294967296); +select lpad('hello', 4294967296); +select lpad('hello', -4294967297); +select lpad('hello', 4294967297); +select lpad('hello', -18446744073709551615); +select lpad('hello', 18446744073709551615); +select lpad('hello', -18446744073709551616); +select lpad('hello', 18446744073709551616); +select lpad('hello', -18446744073709551617); +select lpad('hello', 18446744073709551617); +select lpad('hello', 0, 'x'); +select lpad('hello', 0); + +--echo Check parameters count rpad / lpad +--error ER_WRONG_PARAMCOUNT_TO_NATIVE_FCT +select rpad('x'); +--error ER_WRONG_PARAMCOUNT_TO_NATIVE_FCT +select rpad('x',2,'.','z'); + +--error ER_WRONG_PARAMCOUNT_TO_NATIVE_FCT +select lpad('x'); +--error ER_WRONG_PARAMCOUNT_TO_NATIVE_FCT +select lpad('x',2,'.','z'); # # BUG#17047: CHAR() and IN() can return NULL without signaling NULL @@ -1141,6 +1188,8 @@ select substring('abc', cast(2 as unsigned int)); select repeat('a', cast(2 as unsigned int)); select rpad('abc', cast(5 as unsigned integer), 'x'); select lpad('abc', cast(5 as unsigned integer), 'x'); +select rpad('abc', cast(5 as unsigned integer)); +select lpad('abc', cast(5 as unsigned integer)); # # Bug#15757: Wrong SUBSTRING() result when a tmp table was employed. @@ -1403,6 +1452,8 @@ SELECT RIGHT('1', DAY(FROM_UNIXTIME(-1))); SELECT REPEAT('1', DAY(FROM_UNIXTIME(-1))); SELECT RPAD('hi', DAY(FROM_UNIXTIME(-1)),'?'); SELECT LPAD('hi', DAY(FROM_UNIXTIME(-1)),'?'); +SELECT RPAD('hi', DAY(FROM_UNIXTIME(-1))); +SELECT LPAD('hi', DAY(FROM_UNIXTIME(-1))); # # MDEV-4289 Assertion `0' fails in make_sortkey with GROUP_CONCAT, MAKE_SET, GROUP BY diff --git a/sql/item_create.cc b/sql/item_create.cc index 305f62a04b162..f678bb44f2129 100644 --- a/sql/item_create.cc +++ b/sql/item_create.cc @@ -2260,10 +2260,11 @@ class Create_func_log2 : public Create_func_arg1 }; -class Create_func_lpad : public Create_func_arg3 +class Create_func_lpad : public Create_native_func { public: - virtual Item *create_3_arg(THD *thd, Item *arg1, Item *arg2, Item *arg3); + virtual Item *create_native(THD *thd, LEX_CSTRING *name, + List *item_list); static Create_func_lpad s_singleton; @@ -2686,10 +2687,11 @@ class Create_func_round : public Create_native_func }; -class Create_func_rpad : public Create_func_arg3 +class Create_func_rpad : public Create_native_func { public: - virtual Item *create_3_arg(THD *thd, Item *arg1, Item *arg2, Item *arg3); + virtual Item *create_native(THD *thd, LEX_CSTRING *name, + List *item_list); static Create_func_rpad s_singleton; @@ -5791,9 +5793,34 @@ Create_func_log2::create_1_arg(THD *thd, Item *arg1) Create_func_lpad Create_func_lpad::s_singleton; Item* -Create_func_lpad::create_3_arg(THD *thd, Item *arg1, Item *arg2, Item *arg3) +Create_func_lpad::create_native(THD *thd, LEX_CSTRING *name, + List *item_list) { - return new (thd->mem_root) Item_func_lpad(thd, arg1, arg2, arg3); + Item *func= NULL; + int arg_count= item_list ? item_list->elements : 0; + + switch (arg_count) { + case 2: + { + Item *param_1= item_list->pop(); + Item *param_2= item_list->pop(); + func= new (thd->mem_root) Item_func_lpad(thd, param_1, param_2); + break; + } + case 3: + { + Item *param_1= item_list->pop(); + Item *param_2= item_list->pop(); + Item *param_3= item_list->pop(); + func= new (thd->mem_root) Item_func_lpad(thd, param_1, param_2, param_3); + break; + } + default: + my_error(ER_WRONG_PARAMCOUNT_TO_NATIVE_FCT, MYF(0), name->str); + break; + } + + return func; } @@ -6253,9 +6280,34 @@ Create_func_round::create_native(THD *thd, LEX_CSTRING *name, Create_func_rpad Create_func_rpad::s_singleton; Item* -Create_func_rpad::create_3_arg(THD *thd, Item *arg1, Item *arg2, Item *arg3) +Create_func_rpad::create_native(THD *thd, LEX_CSTRING *name, + List *item_list) { - return new (thd->mem_root) Item_func_rpad(thd, arg1, arg2, arg3); + Item *func= NULL; + int arg_count= item_list ? item_list->elements : 0; + + switch (arg_count) { + case 2: + { + Item *param_1= item_list->pop(); + Item *param_2= item_list->pop(); + func= new (thd->mem_root) Item_func_rpad(thd, param_1, param_2); + break; + } + case 3: + { + Item *param_1= item_list->pop(); + Item *param_2= item_list->pop(); + Item *param_3= item_list->pop(); + func= new (thd->mem_root) Item_func_rpad(thd, param_1, param_2, param_3); + break; + } + default: + my_error(ER_WRONG_PARAMCOUNT_TO_NATIVE_FCT, MYF(0), name->str); + break; + } + + return func; } diff --git a/sql/item_strfunc.cc b/sql/item_strfunc.cc index 0e59984ac26b6..4cf3a54af90c5 100644 --- a/sql/item_strfunc.cc +++ b/sql/item_strfunc.cc @@ -3154,9 +3154,20 @@ String *Item_func_binlog_gtid_pos::val_str(String *str) void Item_func_pad::fix_length_and_dec() { - // Handle character set for args[0] and args[2]. - if (agg_arg_charsets_for_string_result(collation, &args[0], 2, 2)) - return; + if (arg_count == 3) + { + // Handle character set for args[0] and args[2]. + if (agg_arg_charsets_for_string_result(collation, &args[0], 2, 2)) + return; + } + else + { + if (agg_arg_charsets_for_string_result(collation, &args[0], 1, 1)) + return; + pad_str.set_charset(collation.collation); + pad_str.append(" ", 1); + } + if (args[1]->const_item()) { ulonglong char_length= (ulonglong) args[1]->val_int(); @@ -3187,11 +3198,15 @@ String *Item_func_rpad::val_str(String *str) longlong count= args[1]->val_int(); longlong byte_count; String *res= args[0]->val_str(str); - String *rpad= args[2]->val_str(&pad_str); + String *rpad= arg_count == 2 ? &pad_str : args[2]->val_str(&pad_str); if (!res || args[1]->null_value || !rpad || ((count < 0) && !args[1]->unsigned_flag)) goto err; + + if (count == 0) + return make_empty_result(); + null_value=0; /* Assumes that the maximum length of a String is < INT_MAX32. */ /* Set here so that rest of code sees out-of-bound value as such. */ @@ -3216,7 +3231,6 @@ String *Item_func_rpad::val_str(String *str) res->length(res->charpos((int) count)); // Shorten result if longer return (res); } - pad_char_length= rpad->numchars(); byte_count= count * collation.collation->mbmaxlen; { @@ -3230,8 +3244,15 @@ String *Item_func_rpad::val_str(String *str) goto err; } } - if (args[2]->null_value || !pad_char_length) - goto err; + + if (arg_count == 3) + { + if (args[2]->null_value || !(pad_char_length= rpad->numchars())) + goto err; + } + else + pad_char_length= 1; // Implicit space + res_byte_length= res->length(); /* Must be done before alloc_buffer */ if (!(res= alloc_buffer(res,str,&tmp_value, (ulong) byte_count))) goto err; @@ -3268,11 +3289,15 @@ String *Item_func_lpad::val_str(String *str) longlong count= args[1]->val_int(); longlong byte_count; String *res= args[0]->val_str(&tmp_value); - String *pad= args[2]->val_str(&pad_str); + String *pad= arg_count == 2 ? &pad_str : args[2]->val_str(&pad_str); if (!res || args[1]->null_value || !pad || ((count < 0) && !args[1]->unsigned_flag)) goto err; + + if (count == 0) + return make_empty_result(); + null_value=0; /* Assumes that the maximum length of a String is < INT_MAX32. */ /* Set here so that rest of code sees out-of-bound value as such. */ @@ -3301,7 +3326,6 @@ String *Item_func_lpad::val_str(String *str) return res; } - pad_char_length= pad->numchars(); byte_count= count * collation.collation->mbmaxlen; { @@ -3316,9 +3340,16 @@ String *Item_func_lpad::val_str(String *str) } } - if (args[2]->null_value || !pad_char_length || - str->alloc((uint32) byte_count)) + if (str->alloc((uint32) byte_count)) goto err; + + if (arg_count == 3) + { + if (args[2]->null_value || !(pad_char_length= pad->numchars())) + goto err; + } + else + pad_char_length= 1; // Implicit space str->length(0); str->set_charset(collation.collation); diff --git a/sql/item_strfunc.h b/sql/item_strfunc.h index 6ec33b02c3c6f..177835d6239de 100644 --- a/sql/item_strfunc.h +++ b/sql/item_strfunc.h @@ -1010,6 +1010,8 @@ class Item_func_pad: public Item_str_func public: Item_func_pad(THD *thd, Item *arg1, Item *arg2, Item *arg3): Item_str_func(thd, arg1, arg2, arg3) {} + Item_func_pad(THD *thd, Item *arg1, Item *arg2): + Item_str_func(thd, arg1, arg2) {} void fix_length_and_dec(); }; @@ -1019,6 +1021,8 @@ class Item_func_rpad :public Item_func_pad public: Item_func_rpad(THD *thd, Item *arg1, Item *arg2, Item *arg3): Item_func_pad(thd, arg1, arg2, arg3) {} + Item_func_rpad(THD *thd, Item *arg1, Item *arg2): + Item_func_pad(thd, arg1, arg2) {} String *val_str(String *); const char *func_name() const { return "rpad"; } Item *get_copy(THD *thd, MEM_ROOT *mem_root) @@ -1031,6 +1035,8 @@ class Item_func_lpad :public Item_func_pad public: Item_func_lpad(THD *thd, Item *arg1, Item *arg2, Item *arg3): Item_func_pad(thd, arg1, arg2, arg3) {} + Item_func_lpad(THD *thd, Item *arg1, Item *arg2): + Item_func_pad(thd, arg1, arg2) {} String *val_str(String *); const char *func_name() const { return "lpad"; } Item *get_copy(THD *thd, MEM_ROOT *mem_root)