summaryrefslogtreecommitdiff
path: root/pp_ctl.c
diff options
context:
space:
mode:
authorDavid Mitchell <davem@iabyn.com>2016-03-30 15:11:26 +0100
committerDavid Mitchell <davem@iabyn.com>2016-03-30 15:11:26 +0100
commitc349b9a040f3048e07809d40d2a1c12e8873b4ca (patch)
treea41b0cc2c8230702254c90f3577c07b2e2da177b /pp_ctl.c
parentaea0412a260d9d7295c0a5bebb8bb6978dc02ccd (diff)
downloadperl-c349b9a040f3048e07809d40d2a1c12e8873b4ca.tar.gz
Improve code comments for some ctx stuff
* in pp_return(), some comments were out of date about how leave_adjust_stacks() is called ; * add a comment to all the functions that pp_return() tail-calls to the effect that they can be tail-called; * make it clearer when/why OPf_SPECIAL is set on OP_LEAVE; * CXt_LOOP_PLAIN can be a while loop as well as a plain block.
Diffstat (limited to 'pp_ctl.c')
-rw-r--r--pp_ctl.c29
1 files changed, 18 insertions, 11 deletions
diff --git a/pp_ctl.c b/pp_ctl.c
index 7b31bbb324..99ff59a0f0 100644
--- a/pp_ctl.c
+++ b/pp_ctl.c
@@ -2052,7 +2052,8 @@ PP(pp_leave)
assert(CxTYPE(cx) == CXt_BLOCK);
if (PL_op->op_flags & OPf_SPECIAL)
- cx->blk_oldpm = PL_curpm; /* fake block should preserve $1 et al */
+ /* fake block should preserve $1 et al; e.g. /(...)/ while ...; */
+ cx->blk_oldpm = PL_curpm;
oldsp = PL_stack_base + cx->blk_oldsp;
gimme = cx->blk_gimme;
@@ -2256,6 +2257,8 @@ PP(pp_leaveloop)
*
* Any changes made to this function may need to be copied to pp_leavesub
* and vice-versa.
+ *
+ * also tail-called by pp_return
*/
PP(pp_leavesublv)
@@ -2397,20 +2400,18 @@ PP(pp_return)
}
/* There are contexts that need popping. Doing this may free the
- * return value(s), so preserve them first, e.g. popping the plain
+ * return value(s), so preserve them first: e.g. popping the plain
* loop here would free $x:
* sub f { { my $x = 1; return $x } }
* We may also need to shift the args down; for example,
* for (1,2) { return 3,4 }
- * leaves 1,2,3,4 on the stack. Both these actions can be done by
- * leave_adjust_stacks(). By calling it with and lvalue "pass
- * all" action, we just bump the ref count and mortalise the args
- * that need it, do a FREETMPS. The "scan the args and maybe copy
- * them" process will be repeated by whoever we tail-call (e.g.
- * pp_leaveeval), where any copying etc will be done. That is to
- * say, in this code path two scans of the args will be done; the
- * first just shifts and preserves; the second is the "real" arg
- * processing, based on the type of return.
+ * leaves 1,2,3,4 on the stack. Both these actions will be done by
+ * leave_adjust_stacks(), along with freeing any temps. Note that
+ * whoever we tail-call (e.g. pp_leaveeval) will also call
+ * leave_adjust_stacks(); however, the second call is likely to
+ * just see a bunch of SvTEMPs with a ref count of 1, and so just
+ * pass them through, rather than copying them again. So this
+ * isn't as inefficient as it sounds.
*/
cx = &cxstack[cxix];
PUTBACK;
@@ -4201,6 +4202,9 @@ PP(pp_entereval)
}
}
+
+/* also tail-called by pp_return */
+
PP(pp_leaveeval)
{
SV **oldsp;
@@ -4307,6 +4311,9 @@ PP(pp_entertry)
return DOCATCH(PL_op->op_next);
}
+
+/* also tail-called by pp_return */
+
PP(pp_leavetry)
{
SV **oldsp;