mirror of
https://github.com/MariaDB/server.git
synced 2025-05-28 13:01:41 +03:00
Fix for bug #22026: Warning when using IF statement and large unsigned bigint
We use INT_RESULT type if all arguments are of type INT for 'if', 'case', 'coalesce' functions regardless of arguments' unsigned flag, so sometimes we can exceed the INT bounds.
This commit is contained in:
parent
8e6f3ab33b
commit
a079f20aa8
@ -3634,3 +3634,33 @@ INSERT into t1 values (1), (2), (3);
|
||||
SELECT * FROM t1 LIMIT 2, -1;
|
||||
ERROR 42000: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '-1' at line 1
|
||||
DROP TABLE t1;
|
||||
create table t1 (a bigint unsigned);
|
||||
insert into t1 values
|
||||
(if(1, 9223372036854775808, 1)),
|
||||
(case when 1 then 9223372036854775808 else 1 end),
|
||||
(coalesce(9223372036854775808, 1));
|
||||
select * from t1;
|
||||
a
|
||||
9223372036854775808
|
||||
9223372036854775808
|
||||
9223372036854775808
|
||||
drop table t1;
|
||||
create table t1 select
|
||||
if(1, 9223372036854775808, 1) i,
|
||||
case when 1 then 9223372036854775808 else 1 end c,
|
||||
coalesce(9223372036854775808, 1) co;
|
||||
show create table t1;
|
||||
Table Create Table
|
||||
t1 CREATE TABLE `t1` (
|
||||
`i` decimal(19,0) NOT NULL default '0',
|
||||
`c` decimal(19,0) NOT NULL default '0',
|
||||
`co` decimal(19,0) NOT NULL default '0'
|
||||
) ENGINE=MyISAM DEFAULT CHARSET=latin1
|
||||
drop table t1;
|
||||
select
|
||||
if(1, cast(1111111111111111111 as unsigned), 1) i,
|
||||
case when 1 then cast(1111111111111111111 as unsigned) else 1 end c,
|
||||
coalesce(cast(1111111111111111111 as unsigned), 1) co;
|
||||
i c co
|
||||
1111111111111111111 1111111111111111111 1111111111111111111
|
||||
End of 5.0 tests
|
||||
|
@ -3123,3 +3123,27 @@ SELECT * FROM t1 LIMIT 2, -1;
|
||||
|
||||
DROP TABLE t1;
|
||||
|
||||
#
|
||||
# Bug #22026: Warning when using IF statement and large unsigned bigint
|
||||
#
|
||||
|
||||
create table t1 (a bigint unsigned);
|
||||
insert into t1 values
|
||||
(if(1, 9223372036854775808, 1)),
|
||||
(case when 1 then 9223372036854775808 else 1 end),
|
||||
(coalesce(9223372036854775808, 1));
|
||||
select * from t1;
|
||||
drop table t1;
|
||||
create table t1 select
|
||||
if(1, 9223372036854775808, 1) i,
|
||||
case when 1 then 9223372036854775808 else 1 end c,
|
||||
coalesce(9223372036854775808, 1) co;
|
||||
show create table t1;
|
||||
drop table t1;
|
||||
# Ensure we handle big values properly
|
||||
select
|
||||
if(1, cast(1111111111111111111 as unsigned), 1) i,
|
||||
case when 1 then cast(1111111111111111111 as unsigned) else 1 end c,
|
||||
coalesce(cast(1111111111111111111 as unsigned), 1) co;
|
||||
|
||||
--echo End of 5.0 tests
|
||||
|
@ -26,13 +26,17 @@
|
||||
|
||||
static bool convert_constant_item(THD *thd, Field *field, Item **item);
|
||||
|
||||
static Item_result item_store_type(Item_result a,Item_result b)
|
||||
static Item_result item_store_type(Item_result a, Item *item,
|
||||
my_bool unsigned_flag)
|
||||
{
|
||||
Item_result b= item->result_type();
|
||||
|
||||
if (a == STRING_RESULT || b == STRING_RESULT)
|
||||
return STRING_RESULT;
|
||||
else if (a == REAL_RESULT || b == REAL_RESULT)
|
||||
return REAL_RESULT;
|
||||
else if (a == DECIMAL_RESULT || b == DECIMAL_RESULT)
|
||||
else if (a == DECIMAL_RESULT || b == DECIMAL_RESULT ||
|
||||
unsigned_flag != item->unsigned_flag)
|
||||
return DECIMAL_RESULT;
|
||||
else
|
||||
return INT_RESULT;
|
||||
@ -41,6 +45,7 @@ static Item_result item_store_type(Item_result a,Item_result b)
|
||||
static void agg_result_type(Item_result *type, Item **items, uint nitems)
|
||||
{
|
||||
Item **item, **item_end;
|
||||
my_bool unsigned_flag= 0;
|
||||
|
||||
*type= STRING_RESULT;
|
||||
/* Skip beginning NULL items */
|
||||
@ -49,6 +54,7 @@ static void agg_result_type(Item_result *type, Item **items, uint nitems)
|
||||
if ((*item)->type() != Item::NULL_ITEM)
|
||||
{
|
||||
*type= (*item)->result_type();
|
||||
unsigned_flag= (*item)->unsigned_flag;
|
||||
item++;
|
||||
break;
|
||||
}
|
||||
@ -57,7 +63,7 @@ static void agg_result_type(Item_result *type, Item **items, uint nitems)
|
||||
for (; item < item_end; item++)
|
||||
{
|
||||
if ((*item)->type() != Item::NULL_ITEM)
|
||||
*type= item_store_type(type[0], (*item)->result_type());
|
||||
*type= item_store_type(*type, *item, unsigned_flag);
|
||||
}
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user