summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorFather Chrysostomos <sprout@cpan.org>2014-10-20 17:16:01 -0700
committerFather Chrysostomos <sprout@cpan.org>2014-10-20 17:51:51 -0700
commit8538e2d4d47f3b235052cbaabfe1aa035ae18916 (patch)
tree111a5d2413e691c0db3ae60c2707411dfa022b79 /lib
parent40ba772c3f3fa292e5635bb62c0a68609c27fcdb (diff)
downloadperl-8538e2d4d47f3b235052cbaabfe1aa035ae18916.tar.gz
Rmv restrictions on op tree structure for padrange
The padrange optimisation was only happening if the op tree was laid out in a way that would allow B::Deparse easily to restore the origi- nal op_next pointers (via $B::overlay) for the sake of deparsing. It turns out that B::Deparse doesn’t even use the op_next pointers (except for deparsing ‘use’ statements, which are not affected here), so there is no need for these restrictions. In the case of my($a,$b)=@_, @_ was expected to be the sibling of the preceding pushmark-cum-padrange. Removing that restriction doesn’t allow the padrange optimisation to happen in any new cases as far as I can tell. It just means there is less checking to do. In the more general case of a list of lexicals with no =@_, this allows padrange to be used for array and hash slices in conjunction with a separate list-in-list-context optimisation, that formerly con- flicted with padrange. When we compile @a[$lex1,$lex2], we end up with a redundant list-in- list-context: 7 aslice 1 pushmark 5 list 2 pushmark 3 padsv 4 padsv 6 padav (assuming the array is lexical Pushmark pushes a mark on to the markstack, and list pops one, so pushmark and list cancel each other out in list context. In 5.18, when padrange was introduced, this was optimised like this: 5 aslice 1 pushmark 3 list 2 padrange - padsv - padsv 4 padav Then a separate optimisation was added in 5.20 that allows a list with a pushmark kid to turn into null ops, and this cancelled out the padrange: 5 aslice 1 pushmark - ex-list - ex-pushmark 2 padsv 3 padsv 4 padav Bunchmarks show that this is slightly faster than padrange with two lexicals, but more lexicals would make padrange faster. This commit brings us the goodness of both optimisations at once: 3 aslice 1 padrange - ex-list - ex-pushmark - padsv - padsv 2 padav And it is faster than just one optimisation.
Diffstat (limited to 'lib')
-rw-r--r--lib/B/Deparse.pm3
1 files changed, 0 insertions, 3 deletions
diff --git a/lib/B/Deparse.pm b/lib/B/Deparse.pm
index 3866f328b4..dd848e3043 100644
--- a/lib/B/Deparse.pm
+++ b/lib/B/Deparse.pm
@@ -358,9 +358,6 @@ sub _pessimise_walk {
type => OP_PUSHMARK,
name => 'pushmark',
private => ($op->private & OPpLVAL_INTRO),
- next => ($op->flags & OPf_SPECIAL)
- ? $op->sibling->first
- : $op->sibling,
};
}