Commit ec6c4fad authored by malff@lambda.hsd1.co.comcast.net.'s avatar malff@lambda.hsd1.co.comcast.net.
Browse files

Merge lambda.hsd1.co.comcast.net.:/home/malff/TREE/mysql-5.0-33618

into  lambda.hsd1.co.comcast.net.:/home/malff/TREE/mysql-5.1-33618
parents e5ed653e 7bd56cfa
Loading
Loading
Loading
Loading
+109 −0
Original line number Diff line number Diff line
@@ -733,6 +733,115 @@ optimizer: keep hreturn
drop table t1;
drop procedure proc_26977_broken;
drop procedure proc_26977_works;
drop procedure if exists proc_33618_h;
drop procedure if exists proc_33618_c;
create procedure proc_33618_h(num int)
begin
declare count1 int default '0';
declare vb varchar(30);
declare last_row int;
while(num>=1) do
set num=num-1;
begin
declare cur1 cursor for select `a` from t_33618;
declare continue handler for not found set last_row = 1;
set last_row:=0;
open cur1;
rep1:
repeat
begin
declare exit handler for 1062 begin end;
fetch cur1 into vb;
if (last_row = 1) then
## should generate a hpop instruction here
leave rep1;
end if;
end;
until last_row=1
end repeat;
close cur1;
end;
end while;
end//
create procedure proc_33618_c(num int)
begin
declare count1 int default '0';
declare vb varchar(30);
declare last_row int;
while(num>=1) do
set num=num-1;
begin
declare cur1 cursor for select `a` from t_33618;
declare continue handler for not found set last_row = 1;
set last_row:=0;
open cur1;
rep1:
repeat
begin
declare cur2 cursor for select `b` from t_33618;
fetch cur1 into vb;
if (last_row = 1) then
## should generate a cpop instruction here
leave rep1;
end if;
end;
until last_row=1
end repeat;
close cur1;
end;
end while;
end//
show procedure code proc_33618_h;
Pos	Instruction
0	set count1@1 _latin1'0'
1	set vb@2 NULL
2	set last_row@3 NULL
3	jump_if_not 24(24) (num@0 >= 1)
4	set num@0 (num@0 - 1)
5	cpush cur1@0
6	hpush_jump 9 4 CONTINUE
7	set last_row@3 1
8	hreturn 4
9	set last_row@3 0
10	copen cur1@0
11	hpush_jump 13 4 EXIT
12	hreturn 0 17
13	cfetch cur1@0 vb@2
14	jump_if_not 17(17) (last_row@3 = 1)
15	hpop 1
16	jump 19
17	hpop 1
18	jump_if_not 11(19) (last_row@3 = 1)
19	cclose cur1@0
20	hpop 1
21	cpop 1
22	jump 3
show procedure code proc_33618_c;
Pos	Instruction
0	set count1@1 _latin1'0'
1	set vb@2 NULL
2	set last_row@3 NULL
3	jump_if_not 23(23) (num@0 >= 1)
4	set num@0 (num@0 - 1)
5	cpush cur1@0
6	hpush_jump 9 4 CONTINUE
7	set last_row@3 1
8	hreturn 4
9	set last_row@3 0
10	copen cur1@0
11	cpush cur2@1
12	cfetch cur1@0 vb@2
13	jump_if_not 16(16) (last_row@3 = 1)
14	cpop 1
15	jump 18
16	cpop 1
17	jump_if_not 11(18) (last_row@3 = 1)
18	cclose cur1@0
19	hpop 1
20	cpop 1
21	jump 3
drop procedure proc_33618_h;
drop procedure proc_33618_c;
End of 5.0 tests.
CREATE PROCEDURE p1() 
BEGIN 
+77 −0
Original line number Diff line number Diff line
@@ -520,6 +520,83 @@ drop table t1;
drop procedure proc_26977_broken;
drop procedure proc_26977_works;

#
# Bug#33618 Crash in sp_rcontext
#

--disable_warnings
drop procedure if exists proc_33618_h;
drop procedure if exists proc_33618_c;
--enable_warnings

delimiter //;

create procedure proc_33618_h(num int)
begin
  declare count1 int default '0';
  declare vb varchar(30);
  declare last_row int;
        
  while(num>=1) do
    set num=num-1;
    begin
      declare cur1 cursor for select `a` from t_33618;
      declare continue handler for not found set last_row = 1;
      set last_row:=0;
      open cur1;
      rep1:
      repeat
        begin
          declare exit handler for 1062 begin end;
          fetch cur1 into vb;
          if (last_row = 1) then
            ## should generate a hpop instruction here
            leave rep1;
          end if;
        end;
        until last_row=1
      end repeat;
      close cur1;
    end;
  end while;
end//

create procedure proc_33618_c(num int)
begin
  declare count1 int default '0';
  declare vb varchar(30);
  declare last_row int;
        
  while(num>=1) do
    set num=num-1;
    begin
      declare cur1 cursor for select `a` from t_33618;
      declare continue handler for not found set last_row = 1;
      set last_row:=0;
      open cur1;
      rep1:
      repeat
        begin
          declare cur2 cursor for select `b` from t_33618;
          fetch cur1 into vb;
          if (last_row = 1) then
            ## should generate a cpop instruction here
            leave rep1;
          end if;
        end;
        until last_row=1
      end repeat;
      close cur1;
    end;
  end while;
end//
delimiter ;//

show procedure code proc_33618_h;
show procedure code proc_33618_c;

drop procedure proc_33618_h;
drop procedure proc_33618_c;

--echo End of 5.0 tests.

+6 −0
Original line number Diff line number Diff line
@@ -2074,12 +2074,18 @@ sp_head::backpatch(sp_label_t *lab)
  uint dest= instructions();
  List_iterator_fast<bp_t> li(m_backpatch);

  DBUG_ENTER("sp_head::backpatch");
  while ((bp= li++))
  {
    if (bp->lab == lab)
    {
      DBUG_PRINT("info", ("backpatch: (m_ip %d, label 0x%lx <%s>) to dest %d",
                          bp->instr->m_ip, (ulong) lab, lab->name, dest));
      bp->instr->backpatch(dest, lab->ctx);
    }
  }
  DBUG_VOID_RETURN;
}

/*
  Prepare an instance of Create_field for field creation (fill all necessary
+3 −2
Original line number Diff line number Diff line
@@ -877,7 +877,8 @@ class sp_instr_jump : public sp_instr_opt_meta

  virtual void backpatch(uint dest, sp_pcontext *dst_ctx)
  {
    if (m_dest == 0)		// Don't reset
    /* Calling backpatch twice is a logic flaw in jump resolution. */
    DBUG_ASSERT(m_dest == 0);
    m_dest= dest;
  }

+75 −1
Original line number Diff line number Diff line
@@ -314,17 +314,91 @@ sp_rcontext::handle_error(uint sql_errno,
void
sp_rcontext::push_cursor(sp_lex_keeper *lex_keeper, sp_instr_cpush *i)
{
  DBUG_ENTER("sp_rcontext::push_cursor");
  DBUG_ASSERT(m_ccount < m_root_parsing_ctx->max_cursor_index());
  m_cstack[m_ccount++]= new sp_cursor(lex_keeper, i);
  DBUG_PRINT("info", ("m_ccount: %d", m_ccount));
  DBUG_VOID_RETURN;
}


void
sp_rcontext::pop_cursors(uint count)
{
  DBUG_ENTER("sp_rcontext::pop_cursors");
  DBUG_ASSERT(m_ccount >= count);
  while (count--)
  {
    delete m_cstack[--m_ccount];
  }
  DBUG_PRINT("info", ("m_ccount: %d", m_ccount));
  DBUG_VOID_RETURN;
}

void
sp_rcontext::push_handler(struct sp_cond_type *cond, uint h, int type, uint f)
{
  DBUG_ENTER("sp_rcontext::push_handler");
  DBUG_ASSERT(m_hcount < m_root_parsing_ctx->max_handler_index());

  m_handler[m_hcount].cond= cond;
  m_handler[m_hcount].handler= h;
  m_handler[m_hcount].type= type;
  m_handler[m_hcount].foffset= f;
  m_hcount+= 1;

  DBUG_PRINT("info", ("m_hcount: %d", m_hcount));
  DBUG_VOID_RETURN;
}

void
sp_rcontext::pop_handlers(uint count)
{
  DBUG_ENTER("sp_rcontext::pop_handlers");
  DBUG_ASSERT(m_hcount >= count);
  m_hcount-= count;
  DBUG_PRINT("info", ("m_hcount: %d", m_hcount));
  DBUG_VOID_RETURN;
}

void
sp_rcontext::push_hstack(uint h)
{
  DBUG_ENTER("sp_rcontext::push_hstack");
  DBUG_ASSERT(m_hsp < m_root_parsing_ctx->max_handler_index());
  m_hstack[m_hsp++]= h;
  DBUG_PRINT("info", ("m_hsp: %d", m_hsp));
  DBUG_VOID_RETURN;
}

uint
sp_rcontext::pop_hstack()
{
  uint handler;
  DBUG_ENTER("sp_rcontext::pop_hstack");
  DBUG_ASSERT(m_hsp);
  handler= m_hstack[--m_hsp];
  DBUG_PRINT("info", ("m_hsp: %d", m_hsp));
  DBUG_RETURN(handler);
}

void
sp_rcontext::enter_handler(int hid)
{
  DBUG_ENTER("sp_rcontext::enter_handler");
  DBUG_ASSERT(m_ihsp < m_root_parsing_ctx->max_handler_index());
  m_in_handler[m_ihsp++]= hid;
  DBUG_PRINT("info", ("m_ihsp: %d", m_ihsp));
  DBUG_VOID_RETURN;
}

void
sp_rcontext::exit_handler()
{
  DBUG_ENTER("sp_rcontext::exit_handler");
  DBUG_ASSERT(m_ihsp);
  m_ihsp-= 1;
  DBUG_PRINT("info", ("m_ihsp: %d", m_ihsp));
  DBUG_VOID_RETURN;
}


Loading