diff options
author | Father Chrysostomos <sprout@cpan.org> | 2014-10-16 21:52:32 -0700 |
---|---|---|
committer | Father Chrysostomos <sprout@cpan.org> | 2014-10-20 13:05:41 -0700 |
commit | 6aa683079638ed0b1923473b64317a0ef3a99849 (patch) | |
tree | 99e2ce6ec709da94bcc4c692ee3aa6512dc255ca /embed.h | |
parent | 82ce0493f7a0b47a207f493f68ab035a48f2284b (diff) | |
download | perl-6aa683079638ed0b1923473b64317a0ef3a99849.tar.gz |
Make null list+pushmark happen in more cases
This optimisation, added in 7d3c8a683, nulls the list+pushmark pair if
it occurs in list context, since the two ops effectively cancel each
other out. I recently extended it in 8717a761e to apply to void con-
text, too.
It works by checking in the peephole optimiser whether the sibling of
the current op is a list with a pushmark kid:
1 current op
4 list
2 pushmark
3 ...
5 ...
That means the optimisation doesn’t happen if the elder sibling of the
list op is something that is not part of the execution chain, such as
$package_var:
- ex-rv2sv
1 gvsv
4 list
2 pushmark
3 ...
5 ...
because the ex-rv2sv is never the ‘current op’. So ($_,($_,$_))
doesn’t get optimised.
We can’t just handle this when ‘pushmark’ or ‘list’ is the current
op, because, in the former case, there is no way to get to the parent
op to null it; in the latter case, there is no way to get to the op
pointing to pushmark, to rethread the op_next pointers.
However, handling this when list or void context is applied, before we
even get to the peephole optimiser, just works, and requires much less
code. We can just null the ops there, and leave it to the peephole
optimiser’s handling of null ops to rethread op_next pointers.
This breaks this convention:
op_prepend_elem(OP_LIST, foo, list(that_list))
by creating two redundant null ops that were not there before, but the
only pieces of code doing that were calling list() needlessly anyway.
Diffstat (limited to 'embed.h')
-rw-r--r-- | embed.h | 1 |
1 files changed, 0 insertions, 1 deletions
@@ -1537,7 +1537,6 @@ #define new_logop(a,b,c,d) S_new_logop(aTHX_ a,b,c,d) #define no_bareword_allowed(a) S_no_bareword_allowed(aTHX_ a) #define no_fh_allowed(a) S_no_fh_allowed(aTHX_ a) -#define null_listop_in_list_context(a) S_null_listop_in_list_context(aTHX_ a) #define op_integerize(a) S_op_integerize(aTHX_ a) #define op_std_init(a) S_op_std_init(aTHX_ a) #define pmtrans(a,b,c) S_pmtrans(aTHX_ a,b,c) |