mirror of
https://github.com/MariaDB/server.git
synced 2025-07-30 16:24:05 +03:00
A fix and test case for Bug#9777 " Empty set returned by Prepared Statement when it
should return a non empty one" (see comments for the changed files for details). mysql-test/r/ps.result: A test case for Bug#9777: tests results fixed. mysql-test/t/ps.test: A test case for Bug#9777 sql/item.cc: A fix for Bug#9777: when creating a constant item from within Item_int_with_ref::new_item, create the item by value, not by name. This should work with prepared statements placeholders. Item_int_with_ref is a special optimization case used when we compare datetime constants with datetime value. Converting the item to integer early is OK as it is in line with the purpose of Item_int_with_ref - to speed up comparison by using integers. Minor cleanups. sql/item.h: Declaration for Item_int_with_ref::new_item
This commit is contained in:
@ -519,3 +519,41 @@ c1 c2
|
|||||||
200887 860
|
200887 860
|
||||||
200887 200887
|
200887 200887
|
||||||
deallocate prepare stmt;
|
deallocate prepare stmt;
|
||||||
|
drop table t1;
|
||||||
|
create table t1 (
|
||||||
|
id bigint(20) not null auto_increment,
|
||||||
|
code varchar(20) character set utf8 collate utf8_bin not null default '',
|
||||||
|
company_name varchar(250) character set utf8 collate utf8_bin default null,
|
||||||
|
setup_mode tinyint(4) default null,
|
||||||
|
start_date datetime default null,
|
||||||
|
primary key (id), unique key code (code)
|
||||||
|
);
|
||||||
|
create table t2 (
|
||||||
|
id bigint(20) not null auto_increment,
|
||||||
|
email varchar(250) character set utf8 collate utf8_bin default null,
|
||||||
|
name varchar(250) character set utf8 collate utf8_bin default null,
|
||||||
|
t1_id bigint(20) default null,
|
||||||
|
password varchar(250) character set utf8 collate utf8_bin default null,
|
||||||
|
primary_contact tinyint(4) not null default '0',
|
||||||
|
email_opt_in tinyint(4) not null default '1',
|
||||||
|
primary key (id), unique key email (email), key t1_id (t1_id),
|
||||||
|
constraint t2_fk1 foreign key (t1_id) references t1 (id)
|
||||||
|
);
|
||||||
|
insert into t1 values
|
||||||
|
(1, 'demo', 'demo s', 0, current_date()),
|
||||||
|
(2, 'code2', 'name 2', 0, current_date()),
|
||||||
|
(3, 'code3', 'name 3', 0, current_date());
|
||||||
|
insert into t2 values
|
||||||
|
(2, 'email1', 'name1', 3, 'password1', 0, 0),
|
||||||
|
(3, 'email2', 'name1', 1, 'password2', 1, 0),
|
||||||
|
(5, 'email3', 'name3', 2, 'password3', 0, 0);
|
||||||
|
prepare stmt from 'select t2.id from t2, t1 where (t1.id=? and t2.t1_id=t1.id)';
|
||||||
|
set @a=1;
|
||||||
|
execute stmt using @a;
|
||||||
|
id
|
||||||
|
3
|
||||||
|
select t2.id from t2, t1 where (t1.id=1 and t2.t1_id=t1.id);
|
||||||
|
id
|
||||||
|
3
|
||||||
|
deallocate prepare stmt;
|
||||||
|
drop table t1, t2;
|
||||||
|
@ -522,3 +522,50 @@ set @a=200887, @b=860;
|
|||||||
# this query did not return all matching rows
|
# this query did not return all matching rows
|
||||||
execute stmt using @a, @b;
|
execute stmt using @a, @b;
|
||||||
deallocate prepare stmt;
|
deallocate prepare stmt;
|
||||||
|
drop table t1;
|
||||||
|
|
||||||
|
#
|
||||||
|
# Bug#9777 - another occurrence of the problem stated in Bug#9096:
|
||||||
|
# we can not compare basic constants by their names, because a placeholder
|
||||||
|
# is a basic constant while his name is always '?'
|
||||||
|
#
|
||||||
|
|
||||||
|
create table t1 (
|
||||||
|
id bigint(20) not null auto_increment,
|
||||||
|
code varchar(20) character set utf8 collate utf8_bin not null default '',
|
||||||
|
company_name varchar(250) character set utf8 collate utf8_bin default null,
|
||||||
|
setup_mode tinyint(4) default null,
|
||||||
|
start_date datetime default null,
|
||||||
|
primary key (id), unique key code (code)
|
||||||
|
);
|
||||||
|
|
||||||
|
create table t2 (
|
||||||
|
id bigint(20) not null auto_increment,
|
||||||
|
email varchar(250) character set utf8 collate utf8_bin default null,
|
||||||
|
name varchar(250) character set utf8 collate utf8_bin default null,
|
||||||
|
t1_id bigint(20) default null,
|
||||||
|
password varchar(250) character set utf8 collate utf8_bin default null,
|
||||||
|
primary_contact tinyint(4) not null default '0',
|
||||||
|
email_opt_in tinyint(4) not null default '1',
|
||||||
|
primary key (id), unique key email (email), key t1_id (t1_id),
|
||||||
|
constraint t2_fk1 foreign key (t1_id) references t1 (id)
|
||||||
|
);
|
||||||
|
|
||||||
|
insert into t1 values
|
||||||
|
(1, 'demo', 'demo s', 0, current_date()),
|
||||||
|
(2, 'code2', 'name 2', 0, current_date()),
|
||||||
|
(3, 'code3', 'name 3', 0, current_date());
|
||||||
|
|
||||||
|
insert into t2 values
|
||||||
|
(2, 'email1', 'name1', 3, 'password1', 0, 0),
|
||||||
|
(3, 'email2', 'name1', 1, 'password2', 1, 0),
|
||||||
|
(5, 'email3', 'name3', 2, 'password3', 0, 0);
|
||||||
|
|
||||||
|
prepare stmt from 'select t2.id from t2, t1 where (t1.id=? and t2.t1_id=t1.id)';
|
||||||
|
set @a=1;
|
||||||
|
execute stmt using @a;
|
||||||
|
|
||||||
|
select t2.id from t2, t1 where (t1.id=1 and t2.t1_id=t1.id);
|
||||||
|
|
||||||
|
deallocate prepare stmt;
|
||||||
|
drop table t1, t2;
|
||||||
|
24
sql/item.cc
24
sql/item.cc
@ -769,6 +769,13 @@ Item_uint::Item_uint(const char *str_arg, uint length):
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Item_uint::Item_uint(const char *str_arg, longlong i, uint length):
|
||||||
|
Item_int(str_arg, i, length)
|
||||||
|
{
|
||||||
|
unsigned_flag= 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
String *Item_uint::val_str(String *str)
|
String *Item_uint::val_str(String *str)
|
||||||
{
|
{
|
||||||
// following assert is redundant, because fixed=1 assigned in constructor
|
// following assert is redundant, because fixed=1 assigned in constructor
|
||||||
@ -1377,7 +1384,9 @@ Item_param::new_item()
|
|||||||
case NULL_VALUE:
|
case NULL_VALUE:
|
||||||
return new Item_null(name);
|
return new Item_null(name);
|
||||||
case INT_VALUE:
|
case INT_VALUE:
|
||||||
return new Item_int(name, value.integer, max_length);
|
return (unsigned_flag ?
|
||||||
|
new Item_uint(name, value.integer, max_length) :
|
||||||
|
new Item_int(name, value.integer, max_length));
|
||||||
case REAL_VALUE:
|
case REAL_VALUE:
|
||||||
return new Item_real(name, value.real, decimals, max_length);
|
return new Item_real(name, value.real, decimals, max_length);
|
||||||
case STRING_VALUE:
|
case STRING_VALUE:
|
||||||
@ -2023,6 +2032,19 @@ bool Item_int::eq(const Item *arg, bool binary_cmp) const
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Item *Item_int_with_ref::new_item()
|
||||||
|
{
|
||||||
|
DBUG_ASSERT(ref->basic_const_item());
|
||||||
|
/*
|
||||||
|
We need to evaluate the constant to make sure it works with
|
||||||
|
parameter markers.
|
||||||
|
*/
|
||||||
|
return (ref->unsigned_flag ?
|
||||||
|
new Item_uint(ref->name, ref->val_int(), ref->max_length) :
|
||||||
|
new Item_int(ref->name, ref->val_int(), ref->max_length));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
Item_num *Item_uint::neg()
|
Item_num *Item_uint::neg()
|
||||||
{
|
{
|
||||||
return new Item_real(name, - ((double) value), 0, max_length);
|
return new Item_real(name, - ((double) value), 0, max_length);
|
||||||
|
@ -651,6 +651,7 @@ class Item_uint :public Item_int
|
|||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
Item_uint(const char *str_arg, uint length);
|
Item_uint(const char *str_arg, uint length);
|
||||||
|
Item_uint(const char *str_arg, longlong i, uint length);
|
||||||
Item_uint(uint32 i) :Item_int((longlong) i, 10)
|
Item_uint(uint32 i) :Item_int((longlong) i, 10)
|
||||||
{ unsigned_flag= 1; }
|
{ unsigned_flag= 1; }
|
||||||
double val()
|
double val()
|
||||||
@ -1046,11 +1047,7 @@ public:
|
|||||||
{
|
{
|
||||||
return ref->save_in_field(field, no_conversions);
|
return ref->save_in_field(field, no_conversions);
|
||||||
}
|
}
|
||||||
Item *new_item()
|
Item *new_item();
|
||||||
{
|
|
||||||
return (ref->unsigned_flag)? new Item_uint(ref->name, ref->max_length) :
|
|
||||||
new Item_int(ref->name, ref->max_length);
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user