mirror of
https://github.com/MariaDB/server.git
synced 2026-01-06 05:22:24 +03:00
Fixed BUG#4941: Stored procedure crash fetching null value into variable.
mysql-test/r/sp.result: New test case for BUG#4941. mysql-test/t/sp.test: New test case for BUG#4941. sql/protocol_cursor.cc: Handle null values. sql/sp_rcontext.cc: Handle null values.
This commit is contained in:
@@ -1833,6 +1833,22 @@ NULL
|
||||
Warnings:
|
||||
Warning 1311 Referring to uninitialized variable v
|
||||
drop function bug4487|
|
||||
drop procedure if exists bug4941|
|
||||
create procedure bug4941(out x int)
|
||||
begin
|
||||
declare c cursor for select i from t2 limit 1;
|
||||
open c;
|
||||
fetch c into x;
|
||||
close c;
|
||||
end|
|
||||
insert into t2 values (null, null, null)|
|
||||
set @x = 42|
|
||||
call bug4941(@x)|
|
||||
select @x|
|
||||
@x
|
||||
NULL
|
||||
delete from t1|
|
||||
drop procedure bug4941|
|
||||
drop table if exists fac|
|
||||
create table fac (n int unsigned not null primary key, f bigint unsigned)|
|
||||
create procedure ifac(n int unsigned)
|
||||
|
||||
@@ -2000,6 +2000,28 @@ select bug4487()|
|
||||
drop function bug4487|
|
||||
|
||||
|
||||
#
|
||||
# BUG#4941: Stored procedure crash fetching null value into variable.
|
||||
#
|
||||
--disable_warnings
|
||||
drop procedure if exists bug4941|
|
||||
--enable_warnings
|
||||
create procedure bug4941(out x int)
|
||||
begin
|
||||
declare c cursor for select i from t2 limit 1;
|
||||
open c;
|
||||
fetch c into x;
|
||||
close c;
|
||||
end|
|
||||
|
||||
insert into t2 values (null, null, null)|
|
||||
set @x = 42|
|
||||
call bug4941(@x)|
|
||||
select @x|
|
||||
delete from t1|
|
||||
drop procedure bug4941|
|
||||
|
||||
|
||||
#
|
||||
# Some "real" examples
|
||||
#
|
||||
|
||||
@@ -112,7 +112,8 @@ bool Protocol_cursor::write()
|
||||
|
||||
for (; cur_field < fields_end; ++cur_field, ++data_tmp)
|
||||
{
|
||||
if ((len= net_field_length((uchar **)&cp)) == 0)
|
||||
if ((len= net_field_length((uchar **)&cp)) == 0 ||
|
||||
len == NULL_LENGTH)
|
||||
{
|
||||
*data_tmp= 0;
|
||||
}
|
||||
|
||||
@@ -230,21 +230,24 @@ sp_cursor::fetch(THD *thd, List<struct sp_pvar> *vars)
|
||||
return -1;
|
||||
}
|
||||
s= row[fldcount];
|
||||
switch (sp_map_result_type(pv->type))
|
||||
{
|
||||
case INT_RESULT:
|
||||
it= new Item_int(s);
|
||||
break;
|
||||
case REAL_RESULT:
|
||||
it= new Item_real(s, strlen(s));
|
||||
break;
|
||||
default:
|
||||
if (!s)
|
||||
it= new Item_null();
|
||||
else
|
||||
switch (sp_map_result_type(pv->type))
|
||||
{
|
||||
uint len= strlen(s);
|
||||
it= new Item_string(thd->strmake(s, len), len, thd->db_charset);
|
||||
case INT_RESULT:
|
||||
it= new Item_int(s);
|
||||
break;
|
||||
case REAL_RESULT:
|
||||
it= new Item_real(s, strlen(s));
|
||||
break;
|
||||
default:
|
||||
{
|
||||
uint len= strlen(s);
|
||||
it= new Item_string(thd->strmake(s, len), len, thd->db_charset);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
thd->spcont->set_item(pv->offset, it);
|
||||
}
|
||||
if (fldcount < m_prot->get_field_count())
|
||||
|
||||
Reference in New Issue
Block a user