summaryrefslogtreecommitdiff
path: root/pp_ctl.c
diff options
context:
space:
mode:
authorDave Mitchell <davem@fdisolutions.com>2004-08-14 22:32:16 +0000
committerDave Mitchell <davem@fdisolutions.com>2004-08-14 22:32:16 +0000
commita45cdc79a7c02a2ea3f4f147e8200ca60d683da5 (patch)
tree579970e6daa1c9694d1ddf9d0b749c38acaeabd5 /pp_ctl.c
parent90d1b12917c6df69d793f0c9dc8d5cbfacf97955 (diff)
downloadperl-a45cdc79a7c02a2ea3f4f147e8200ca60d683da5.tar.gz
make pp_goto() cope potential stack reallocation in EXTEND
The code for goto &foo had local pointers to the stack that pointed to the wrong place after a realloc. p4raw-id: //depot/perl@23217
Diffstat (limited to 'pp_ctl.c')
-rw-r--r--pp_ctl.c19
1 files changed, 8 insertions, 11 deletions
diff --git a/pp_ctl.c b/pp_ctl.c
index 4ba11712f1..f07d7162b8 100644
--- a/pp_ctl.c
+++ b/pp_ctl.c
@@ -2267,16 +2267,13 @@ PP(pp_goto)
TOPBLOCK(cx);
if (CxREALEVAL(cx))
DIE(aTHX_ "Can't goto subroutine from an eval-string");
- mark = PL_stack_sp;
if (CxTYPE(cx) == CXt_SUB && cx->blk_sub.hasargs) {
/* put @_ back onto stack */
AV* av = cx->blk_sub.argarray;
items = AvFILLp(av) + 1;
- PL_stack_sp++;
- EXTEND(PL_stack_sp, items); /* @_ could have been extended. */
- Copy(AvARRAY(av), PL_stack_sp, items, SV*);
- PL_stack_sp += items;
+ EXTEND(SP, items+1); /* @_ could have been extended. */
+ Copy(AvARRAY(av), SP + 1, items, SV*);
SvREFCNT_dec(GvAV(PL_defgv));
GvAV(PL_defgv) = cx->blk_sub.savearray;
/* abandon @_ if it got reified */
@@ -2294,11 +2291,11 @@ PP(pp_goto)
AV* av;
av = GvAV(PL_defgv);
items = AvFILLp(av) + 1;
- PL_stack_sp++;
- EXTEND(PL_stack_sp, items); /* @_ could have been extended. */
- Copy(AvARRAY(av), PL_stack_sp, items, SV*);
- PL_stack_sp += items;
+ EXTEND(SP, items+1); /* @_ could have been extended. */
+ Copy(AvARRAY(av), SP + 1, items, SV*);
}
+ mark = SP;
+ SP += items;
if (CxTYPE(cx) == CXt_SUB &&
!(CvDEPTH(cx->blk_sub.cv) = cx->blk_sub.olddepth))
SvREFCNT_dec(cx->blk_sub.cv);
@@ -2331,9 +2328,9 @@ PP(pp_goto)
SV **newsp;
I32 gimme;
- PL_stack_sp--; /* There is no cv arg. */
/* Push a mark for the start of arglist */
PUSHMARK(mark);
+ PUTBACK;
(void)(*CvXSUB(cv))(aTHX_ cv);
/* Pop the current context like a decent sub should */
POPBLOCK(cx, PL_curpm);
@@ -2372,7 +2369,6 @@ PP(pp_goto)
GvAV(PL_defgv) = (AV*)SvREFCNT_inc(av);
CX_CURPAD_SAVE(cx->blk_sub);
cx->blk_sub.argarray = av;
- ++mark;
if (items >= AvMAX(av) + 1) {
ary = AvALLOC(av);
@@ -2387,6 +2383,7 @@ PP(pp_goto)
SvPVX(av) = (char*)ary;
}
}
+ ++mark;
Copy(mark,AvARRAY(av),items,SV*);
AvFILLp(av) = items - 1;
assert(!AvREAL(av));