[perl #49190] Stringify repl repeatedly in s///g
authorFather Chrysostomos <sprout@cpan.org>
Thu, 11 Oct 2012 09:03:35 +0000 (02:03 -0700)
committerFather Chrysostomos <sprout@cpan.org>
Fri, 12 Oct 2012 06:07:35 +0000 (23:07 -0700)
commit1754320d025df69f39aefec8568947369f4b13cb
tree197fa62f4712b007e1310175f9b39fa4e0957bc6
parent2ed8c61f1921fabddfeb2a099733b977cb66ae42
[perl #49190] Stringify repl repeatedly in s///g

pm_runtime in op.c examines the rhs of s/// to see whether it is safe
to execute that set of ops just once.  If it sees a match var or an
expression with side effects, it creates a pp_substcont op, which
results in the rhs being executed multiple times.

If the rhs seems constant enough, pp_subst does the substitution in a
tight loop.

This unfortunately causes s/a/$a/ to fail if *a has been aliased to
*1.  Furthermore, $REGMARK and $REGERROR did not count as match vars.

pp_subst actually has two separate loops.  One of them modifies the
target in place.  The other appends to a new scalar and then copies it
back to the target.  The first loop is used if it seems safe.

This commit makes $REGMARK, $REGERROR and aliases to match vars work=
when the replacement consists solely of the variable.

It does this by setting PL_curpm before stringifying the replacement,
so that $1 et al. see the right pattern.  It also stringifies the
variable for each iteration of the second loop, so that $1 and
$REGMARK update.

The first loop, which requires the rhs to be constant, is skipped if
the regexp contains the special backtracking control verbs that mod-
ify $REGMARK and $REGERROR.
pp_hot.c
t/re/pat_rt_report.t
t/re/subst.t