mirror of
https://github.com/MariaDB/server.git
synced 2025-01-17 20:42:30 +01:00
Merge bk-internal.mysql.com:/home/bk/mysql-5.0
into mysql.com:/usersnfs/pchardin/mysql-5.0 sql/sp_head.cc: Auto merged
This commit is contained in:
commit
996d4c455e
5 changed files with 84 additions and 3 deletions
|
@ -3193,4 +3193,23 @@ set f1= concat( 'hello', f1 );
|
||||||
return f1;
|
return f1;
|
||||||
end|
|
end|
|
||||||
drop function bug9048|
|
drop function bug9048|
|
||||||
|
drop procedure if exists bug12849_1|
|
||||||
|
create procedure bug12849_1(inout x char) select x into x|
|
||||||
|
set @var='a'|
|
||||||
|
call bug12849_1(@var)|
|
||||||
|
select @var|
|
||||||
|
@var
|
||||||
|
a
|
||||||
|
drop procedure bug12849_1|
|
||||||
|
drop procedure if exists bug12849_2|
|
||||||
|
create procedure bug12849_2(inout foo varchar(15))
|
||||||
|
begin
|
||||||
|
select concat(foo, foo) INTO foo;
|
||||||
|
end|
|
||||||
|
set @var='abcd'|
|
||||||
|
call bug12849_2(@var)|
|
||||||
|
select @var|
|
||||||
|
@var
|
||||||
|
abcdabcd
|
||||||
|
drop procedure bug12849_2|
|
||||||
drop table t1,t2;
|
drop table t1,t2;
|
||||||
|
|
|
@ -4043,6 +4043,32 @@ begin
|
||||||
end|
|
end|
|
||||||
drop function bug9048|
|
drop function bug9048|
|
||||||
|
|
||||||
|
#
|
||||||
|
# Bug #12849 Stored Procedure: Crash on procedure call with CHAR type
|
||||||
|
# 'INOUT' parameter
|
||||||
|
#
|
||||||
|
|
||||||
|
--disable_warnings
|
||||||
|
drop procedure if exists bug12849_1|
|
||||||
|
--enable_warnings
|
||||||
|
create procedure bug12849_1(inout x char) select x into x|
|
||||||
|
set @var='a'|
|
||||||
|
call bug12849_1(@var)|
|
||||||
|
select @var|
|
||||||
|
drop procedure bug12849_1|
|
||||||
|
|
||||||
|
--disable_warnings
|
||||||
|
drop procedure if exists bug12849_2|
|
||||||
|
--enable_warnings
|
||||||
|
create procedure bug12849_2(inout foo varchar(15))
|
||||||
|
begin
|
||||||
|
select concat(foo, foo) INTO foo;
|
||||||
|
end|
|
||||||
|
set @var='abcd'|
|
||||||
|
call bug12849_2(@var)|
|
||||||
|
select @var|
|
||||||
|
drop procedure bug12849_2|
|
||||||
|
|
||||||
#
|
#
|
||||||
# BUG#NNNN: New bug synopsis
|
# BUG#NNNN: New bug synopsis
|
||||||
#
|
#
|
||||||
|
|
19
sql/item.cc
19
sql/item.cc
|
@ -818,8 +818,25 @@ String *Item_splocal::val_str(String *sp)
|
||||||
DBUG_ASSERT(fixed);
|
DBUG_ASSERT(fixed);
|
||||||
Item *it= this_item();
|
Item *it= this_item();
|
||||||
String *ret= it->val_str(sp);
|
String *ret= it->val_str(sp);
|
||||||
|
/*
|
||||||
|
This way we mark returned value of val_str as const,
|
||||||
|
so that various functions (e.g. CONCAT) won't try to
|
||||||
|
modify the value of the Item. Analogous mechanism is
|
||||||
|
implemented for Item_param.
|
||||||
|
Without this trick Item_splocal could be changed as a
|
||||||
|
side-effect of expression computation. Here is an example
|
||||||
|
of what happens without it: suppose x is varchar local
|
||||||
|
variable in a SP with initial value 'ab' Then
|
||||||
|
select concat(x,'c');
|
||||||
|
would change x's value to 'abc', as Item_func_concat::val_str()
|
||||||
|
would use x's internal buffer to compute the result.
|
||||||
|
This is intended behaviour of Item_func_concat. Comments to
|
||||||
|
Item_param class contain some more details on the topic.
|
||||||
|
*/
|
||||||
|
str_value_ptr.set(ret->ptr(), ret->length(),
|
||||||
|
ret->charset());
|
||||||
null_value= it->null_value;
|
null_value= it->null_value;
|
||||||
return ret;
|
return &str_value_ptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -715,9 +715,17 @@ public:
|
||||||
class Item_splocal : public Item
|
class Item_splocal : public Item
|
||||||
{
|
{
|
||||||
uint m_offset;
|
uint m_offset;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
LEX_STRING m_name;
|
LEX_STRING m_name;
|
||||||
|
|
||||||
|
/*
|
||||||
|
Buffer, pointing to the string value of the item. We need it to
|
||||||
|
protect internal buffer from changes. See comment to analogous
|
||||||
|
member in Item_param for more details.
|
||||||
|
*/
|
||||||
|
String str_value_ptr;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Position of this reference to SP variable in the statement (the
|
Position of this reference to SP variable in the statement (the
|
||||||
statement itself is in sp_instr_stmt::m_query).
|
statement itself is in sp_instr_stmt::m_query).
|
||||||
|
|
|
@ -275,8 +275,19 @@ sp_eval_func_item(THD *thd, Item **it_addr, enum enum_field_types type,
|
||||||
}
|
}
|
||||||
DBUG_PRINT("info",("STRING_RESULT: %*s",
|
DBUG_PRINT("info",("STRING_RESULT: %*s",
|
||||||
s->length(), s->c_ptr_quick()));
|
s->length(), s->c_ptr_quick()));
|
||||||
CHARSET_INFO *itcs= it->collation.collation;
|
/*
|
||||||
CREATE_ON_CALLERS_ARENA(it= new(reuse, &rsize) Item_string(itcs),
|
Reuse mechanism in sp_eval_func_item() is only employed for assignments
|
||||||
|
to local variables and OUT/INOUT SP parameters repsesented by
|
||||||
|
Item_splocal. Usually we have some expression, which needs
|
||||||
|
to be calculated and stored into the local variable. However in the
|
||||||
|
case if "it" equals to "reuse", there is no "calculation" step. So,
|
||||||
|
no reason to employ reuse mechanism to save variable into itself.
|
||||||
|
*/
|
||||||
|
if (it == reuse)
|
||||||
|
DBUG_RETURN(it);
|
||||||
|
|
||||||
|
CREATE_ON_CALLERS_ARENA(it= new(reuse, &rsize)
|
||||||
|
Item_string(it->collation.collation),
|
||||||
use_callers_arena, &backup_arena);
|
use_callers_arena, &backup_arena);
|
||||||
/*
|
/*
|
||||||
We have to use special constructor and allocate string
|
We have to use special constructor and allocate string
|
||||||
|
|
Loading…
Reference in a new issue