summaryrefslogtreecommitdiff
path: root/perl.c
diff options
context:
space:
mode:
authorDavid Mitchell <davem@iabyn.com>2015-07-17 14:44:32 +0100
committerDavid Mitchell <davem@iabyn.com>2016-02-03 08:59:37 +0000
commit8e90e786101d3edc1f7b5ad4b735860d4667dcd4 (patch)
treeae3b2deeed0b2520048ff688e330349a3fca3abf /perl.c
parent9aa350eb0f0c75e5d5ac3fbccd708064f23d6795 (diff)
downloadperl-8e90e786101d3edc1f7b5ad4b735860d4667dcd4.tar.gz
call_sv(), fold_const(): different CX pop test
Perl_call_sv() and S_fold_constants() both have similar code that: pushes an EVAL context, does a JMPENV_PUSH() and CALLRUNOPS(), then optionally pops the EVAL context. The optionally part depends on whether what's doing the dying has already popped the context before long-jumping. Currently the decision on whether to pop is based on whether the scope stack has already been popped. This commit changes that to whether the context stack has already been popped, since shortly we're going to change eval contexts so that the old savestack_ix is stored in the CX struct rather than on the scope stack. I ran this code with some asserts that the two conditions were identical, and nothing failed.
Diffstat (limited to 'perl.c')
-rw-r--r--perl.c11
1 files changed, 8 insertions, 3 deletions
diff --git a/perl.c b/perl.c
index 1d94b38777..a7938bd774 100644
--- a/perl.c
+++ b/perl.c
@@ -2711,7 +2711,6 @@ Perl_call_sv(pTHX_ SV *sv, VOL I32 flags)
METHOP method_op;
I32 oldmark;
VOL I32 retval = 0;
- I32 oldscope;
bool oldcatch = CATCH_GET;
int ret;
OP* const oldop = PL_op;
@@ -2743,7 +2742,6 @@ Perl_call_sv(pTHX_ SV *sv, VOL I32 flags)
PUTBACK;
}
oldmark = TOPMARK;
- oldscope = PL_scopestack_ix;
if (PERLDB_SUB && PL_curstash != PL_debstash
/* Handle first BEGIN of -d. */
@@ -2777,8 +2775,10 @@ Perl_call_sv(pTHX_ SV *sv, VOL I32 flags)
CATCH_SET(oldcatch);
}
else {
+ I32 old_cxix;
myop.op_other = (OP*)&myop;
(void)POPMARK;
+ old_cxix = cxstack_ix;
create_eval_scope(flags|G_FAKINGEVAL);
(void)INCMARK;
@@ -2820,8 +2820,13 @@ Perl_call_sv(pTHX_ SV *sv, VOL I32 flags)
break;
}
- if (PL_scopestack_ix > oldscope)
+ /* if we croaked, depending on how we croaked the eval scope
+ * may or may not have already been popped */
+ if (cxstack_ix > old_cxix) {
+ assert(cxstack_ix == old_cxix + 1);
+ assert(CxTYPE(&cxstack[cxstack_ix]) == CXt_EVAL);
delete_eval_scope();
+ }
JMPENV_POP;
}