summaryrefslogtreecommitdiff
path: root/pp_ctl.c
diff options
context:
space:
mode:
authorDavid Mitchell <davem@iabyn.com>2014-06-27 11:52:44 +0100
committerDavid Mitchell <davem@iabyn.com>2014-07-08 16:40:03 +0100
commit29e61fd971cd4373e17cf1dd6e954ddea5171299 (patch)
tree98cedf27877b50dba8ab0a7c7e781bd4a21275f3 /pp_ctl.c
parentc4b209751862a812e3cb3d6951c4f9411b0ca0af (diff)
downloadperl-29e61fd971cd4373e17cf1dd6e954ddea5171299.tar.gz
add op_lastsib and -DPERL_OP_PARENT
Add the boolean field op_lastsib to OPs. Within the core, this is set on the last op in an op_sibling chain (so it is synonymous with op_sibling being null). By default, its value is set but not used. In addition, add a new build define (not yet enabled by default), -DPERL_OP_PARENT, that forces the core to use op_lastsib to detect the last op in a sibling chain, rather than op_sibling being NULL. This frees up the last op_sibling pointer in the chain, which rather than being set to NULL, is now set to point back to the parent of the sibling chain (if any). This commit also adds a C-level op_parent() function and B parent() method; under default builds they just return NULL, under PERL_OP_PARENT they return the parent of the current op. Collectively this provides a facility not previously available from B:: nor C, of being able to follow an op tree up as well as down.
Diffstat (limited to 'pp_ctl.c')
-rw-r--r--pp_ctl.c11
1 files changed, 7 insertions, 4 deletions
diff --git a/pp_ctl.c b/pp_ctl.c
index b25905d369..7d098b739d 100644
--- a/pp_ctl.c
+++ b/pp_ctl.c
@@ -3035,14 +3035,17 @@ PP(pp_goto) /* also pp_dump */
break;
}
if (gotoprobe) {
+ OP *sibl1, *sibl2;
+
retop = dofindlabel(gotoprobe, label, label_len, label_flags,
enterops, enterops + GOTO_DEPTH);
if (retop)
break;
- if (OP_HAS_SIBLING(gotoprobe) &&
- OP_SIBLING(gotoprobe)->op_type == OP_UNSTACK &&
- OP_HAS_SIBLING(OP_SIBLING(gotoprobe))) {
- retop = dofindlabel(OP_SIBLING(OP_SIBLING(gotoprobe)),
+ if ( (sibl1 = OP_SIBLING(gotoprobe)) &&
+ sibl1->op_type == OP_UNSTACK &&
+ (sibl2 = OP_SIBLING(sibl1)))
+ {
+ retop = dofindlabel(sibl2,
label, label_len, label_flags, enterops,
enterops + GOTO_DEPTH);
if (retop)